diff --git a/Android.mk b/Android.mk
new file mode 100644
index 0000000..b503e0e
--- /dev/null
+++ b/Android.mk
@@ -0,0 +1,28 @@
+# Copyright 2011, The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+LOCAL_PATH := $(call my-dir)
+
+##################################################
+# Static library
+##################################################
+include $(CLEAR_VARS)
+
+LOCAL_MODULE := smackxmpp
+LOCAL_MODULE_TAGS := optional
+LOCAL_SDK_VERSION := 9
+
+LOCAL_SRC_FILES := $(call all-java-files-under,src)
+
+include $(BUILD_STATIC_JAVA_LIBRARY)
diff --git a/README b/README
new file mode 100644
index 0000000..c986de5
--- /dev/null
+++ b/README
@@ -0,0 +1,7 @@
+The directory contains the build environment of smack for Android (located in asmack-master/)
+and the generated source files (located in src/).
+
+To update to the latest smack source. Please run the following:
+
+./update.sh
+m -j24 smackxmpp
diff --git a/asmack-master/build.bash b/asmack-master/build.bash
index 874f238..d291220 100755
--- a/asmack-master/build.bash
+++ b/asmack-master/build.bash
@@ -542,6 +542,16 @@
 createVersionTag
 createbuildsrc
 patchsrc "patch"
+
+##
+## BEGIN Modification for android platform build system
+##
+echo done with android modifications
+exit
+##
+## END Modification for android platform build system
+##
+
 if $BUILD_JINGLE ; then
   patchsrc "jingle"
   JINGLE_ARGS="-Djingle=lib/jstun.jar"
diff --git a/src/META-INF/services/com.kenai.jbosh.HTTPSender b/src/META-INF/services/com.kenai.jbosh.HTTPSender
new file mode 100644
index 0000000..3608d8e
--- /dev/null
+++ b/src/META-INF/services/com.kenai.jbosh.HTTPSender
@@ -0,0 +1 @@
+com.kenai.jbosh.ApacheHTTPSender
diff --git a/src/com/kenai/jbosh/AbstractAttr.java b/src/com/kenai/jbosh/AbstractAttr.java
new file mode 100644
index 0000000..0d6f84c
--- /dev/null
+++ b/src/com/kenai/jbosh/AbstractAttr.java
@@ -0,0 +1,116 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+ package com.kenai.jbosh;
+
+/**
+ * Abstract base class for creating BOSH attribute classes.  Concrete
+ * implementations of this class will naturally inherit the underlying
+ * type's behavior for {@code equals()}, {@code hashCode()},
+ * {@code toString()}, and {@code compareTo()}, allowing for the easy
+ * creation of objects which extend existing trivial types.  This was done
+ * to comply with the prefactoring rule declaring, "when you are being
+ * abstract, be abstract all the way".
+ *
+ * @param <T> type of the extension object
+ */
+abstract class AbstractAttr<T extends Comparable>
+    implements Comparable {
+
+    /**
+     * Captured value.
+     */
+    private final T value;
+
+    /**
+     * Creates a new encapsulated object instance.
+     *
+     * @param aValue encapsulated getValue
+     */
+    protected AbstractAttr(final T aValue) {
+        value = aValue;
+    }
+
+    /**
+     * Gets the encapsulated data value.
+     *
+     * @return data value
+     */
+    public final T getValue() {
+        return value;
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Object method overrides:
+
+    /**
+     * {@inheritDoc}
+     *
+     * @param otherObj object to compare to
+     * @return true if the objects are equal, false otherwise
+     */
+    @Override
+    public boolean equals(final Object otherObj) {
+        if (otherObj == null) {
+            return false;
+        } else if (otherObj instanceof AbstractAttr) {
+            AbstractAttr other =
+                    (AbstractAttr) otherObj;
+            return value.equals(other.value);
+        } else {
+            return false;
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     *
+     * @return hashCode of the encapsulated object
+     */
+    @Override
+    public int hashCode() {
+        return value.hashCode();
+    }
+
+    /**
+     * {@inheritDoc}
+     *
+     * @return string representation of the encapsulated object
+     */
+    @Override
+    public String toString() {
+        return value.toString();
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Comparable interface:
+
+    /**
+     * {@inheritDoc}
+     *
+     * @param otherObj object to compare to
+     * @return -1, 0, or 1
+     */
+    @SuppressWarnings("unchecked")
+    public int compareTo(final Object otherObj) {
+        if (otherObj == null) {
+            return 1;
+        } else {
+            return value.compareTo(otherObj);
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AbstractBody.java b/src/com/kenai/jbosh/AbstractBody.java
new file mode 100644
index 0000000..4d66c8c
--- /dev/null
+++ b/src/com/kenai/jbosh/AbstractBody.java
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.Collections;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Class representing a single message to or from the BOSH connection
+ * manager (CM).
+ * <p/>
+ * These messages consist of a single {@code body} element
+ * (qualified within the BOSH namespace:
+ * {@code http://jabber.org/protocol/httpbind}) and contain zero or more
+ * child elements (of any namespace).  These child elements constitute the
+ * message payload.
+ * <p/>
+ * In addition to the message payload, the attributes of the wrapper
+ * {@code body} element may also need to be used as part of the communication
+ * protocol being implemented on top of BOSH, or to define additional
+ * namespaces used by the child "payload" elements.  These attributes are
+ * exposed via accessors.
+ */
+public abstract class AbstractBody {
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructor:
+
+    /**
+     * Restrict subclasses to the local package.
+     */
+    AbstractBody() {
+        // Empty
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Public methods:
+
+    /**
+     * Get a set of all defined attribute names.
+     *
+     * @return set of qualified attribute names
+     */
+    public final Set<BodyQName> getAttributeNames() {
+        Map<BodyQName, String> attrs = getAttributes();
+        return Collections.unmodifiableSet(attrs.keySet());
+    }
+
+    /**
+     * Get the value of the specified attribute.
+     *
+     * @param attr name of the attribute to retriece
+     * @return attribute value, or {@code null} if not defined
+     */
+    public final String getAttribute(final BodyQName attr) {
+        Map<BodyQName, String> attrs = getAttributes();
+        return attrs.get(attr);
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Abstract methods:
+
+    /**
+     * Get a map of all defined attribute names with their corresponding values.
+     *
+     * @return map of qualified attributes
+     */
+    public abstract Map<BodyQName, String> getAttributes();
+
+    /**
+     * Get an XML String representation of this message. 
+     *
+     * @return XML string representing the body message
+     */
+    public abstract String toXML();
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Returns the qualified name of the root/wrapper element.
+     *
+     * @return qualified name
+     */
+    static BodyQName getBodyQName() {
+        return BodyQName.createBOSH("body");
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AbstractIntegerAttr.java b/src/com/kenai/jbosh/AbstractIntegerAttr.java
new file mode 100644
index 0000000..1b827f9
--- /dev/null
+++ b/src/com/kenai/jbosh/AbstractIntegerAttr.java
@@ -0,0 +1,97 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Abstract base class for attribute implementations based on {@code Integer}
+ * types.  Additional support for parsing of integer values from their
+ * {@code String} representations as well as callback handling of value
+ * validity checks are also provided.
+ */
+abstract class AbstractIntegerAttr extends AbstractAttr<Integer> {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute value
+     * @throws BOSHException on parse or validation failure
+     */
+    protected AbstractIntegerAttr(final int val) throws BOSHException {
+        super(Integer.valueOf(val));
+    }
+    
+    /**
+     * Creates a new attribute object.
+     *
+     * @param val attribute value in string form
+     * @throws BOSHException on parse or validation failure
+     */
+    protected AbstractIntegerAttr(final String val) throws BOSHException {
+        super(parseInt(val));
+    }
+
+    /**
+     * Utility method intended to be called by concrete implementation
+     * classes from within the {@code check()} method when the concrete
+     * class needs to ensure that the integer value does not drop below
+     * the specified minimum value.
+     *
+     * @param minVal minimum value to allow
+     * @throws BOSHException if the integer value is below the specific
+     *  minimum
+     */
+    protected final void checkMinValue(int minVal) throws BOSHException {
+        int intVal = getValue();
+        if (intVal < minVal) {
+            throw(new BOSHException(
+                    "Illegal attribute value '" + intVal + "' provided.  "
+                    + "Must be >= " + minVal));
+        }
+    }
+
+    /**
+     * Utility method to parse a {@code String} into an {@code Integer},
+     * converting any possible {@code NumberFormatException} thrown into
+     * a {@code BOSHException}.
+     *
+     * @param str string to parse
+     * @return integer value
+     * @throws BOSHException on {@code NumberFormatException}
+     */
+    private static int parseInt(final String str) throws BOSHException {
+        try {
+            return Integer.parseInt(str);
+        } catch (NumberFormatException nfx) {
+            throw(new BOSHException(
+                    "Could not parse an integer from the value provided: "
+                    + str,
+                    nfx));
+        }
+    }
+
+    /**
+     * Returns the native {@code int} value of the underlying {@code Integer}.
+     * Will throw {@code NullPointerException} if the underlying
+     * integer was {@code null}.
+     *
+     * @return native {@code int} value
+     */
+    public int intValue() {
+        return getValue().intValue();
+    }
+
+}
diff --git a/src/com/kenai/jbosh/ApacheHTTPResponse.java b/src/com/kenai/jbosh/ApacheHTTPResponse.java
new file mode 100644
index 0000000..9f6731f
--- /dev/null
+++ b/src/com/kenai/jbosh/ApacheHTTPResponse.java
@@ -0,0 +1,253 @@
+/*
+ * Copyright 2009 Guenther Niess
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.IOException;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+
+import org.apache.http.HttpEntity;
+import org.apache.http.HttpResponse;
+import org.apache.http.client.HttpClient;
+import org.apache.http.client.methods.HttpPost;
+import org.apache.http.entity.ByteArrayEntity;
+
+import org.apache.http.protocol.BasicHttpContext;
+import org.apache.http.protocol.HttpContext;
+import org.apache.http.util.EntityUtils;
+
+final class ApacheHTTPResponse implements HTTPResponse {
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constants:
+
+    /**
+     * Name of the accept encoding header.
+     */
+    private static final String ACCEPT_ENCODING = "Accept-Encoding";
+
+    /**
+     * Value to use for the ACCEPT_ENCODING header.
+     */
+    private static final String ACCEPT_ENCODING_VAL =
+            ZLIBCodec.getID() + ", " + GZIPCodec.getID();
+
+    /**
+     * Name of the character set to encode the body to/from.
+     */
+    private static final String CHARSET = "UTF-8";
+
+    /**
+     * Content type to use when transmitting the body data.
+     */
+    private static final String CONTENT_TYPE = "text/xml; charset=utf-8";
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Class variables:
+
+    /**
+     * Lock used for internal synchronization.
+     */
+    private final Lock lock = new ReentrantLock();
+
+    /**
+     * The execution state of an HTTP process.
+     */
+    private final HttpContext context;
+
+    /**
+     * HttpClient instance to use to communicate.
+     */
+    private final HttpClient client;
+
+    /**
+     * The HTTP POST request is sent to the server.
+     */
+    private final HttpPost post;
+
+    /**
+     * A flag which indicates if the transmission was already done.
+     */
+    private boolean sent;
+
+    /**
+     * Exception to throw when the response data is attempted to be accessed,
+     * or {@code null} if no exception should be thrown.
+     */
+    private BOSHException toThrow;
+
+    /**
+     * The response body which was received from the server or {@code null}
+     * if that has not yet happened.
+     */
+    private AbstractBody body;
+
+    /**
+     * The HTTP response status code.
+     */
+    private int statusCode;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Create and send a new request to the upstream connection manager,
+     * providing deferred access to the results to be returned.
+     *
+     * @param client client instance to use when sending the request
+     * @param cfg client configuration
+     * @param params connection manager parameters from the session creation
+     *  response, or {@code null} if the session has not yet been established
+     * @param request body of the client request
+     */
+    ApacheHTTPResponse(
+            final HttpClient client,
+            final BOSHClientConfig cfg,
+            final CMSessionParams params,
+            final AbstractBody request) {
+        super();
+        this.client = client;
+        this.context = new BasicHttpContext();
+        this.post = new HttpPost(cfg.getURI().toString());
+        this.sent = false;
+
+        try {
+            String xml = request.toXML();
+            byte[] data = xml.getBytes(CHARSET);
+
+            String encoding = null;
+            if (cfg.isCompressionEnabled() && params != null) {
+                AttrAccept accept = params.getAccept();
+                if (accept != null) {
+                    if (accept.isAccepted(ZLIBCodec.getID())) {
+                        encoding = ZLIBCodec.getID();
+                        data = ZLIBCodec.encode(data);
+                    } else if (accept.isAccepted(GZIPCodec.getID())) {
+                        encoding = GZIPCodec.getID();
+                        data = GZIPCodec.encode(data);
+                    }
+                }
+            }
+
+            ByteArrayEntity entity = new ByteArrayEntity(data);
+            entity.setContentType(CONTENT_TYPE);
+            if (encoding != null) {
+                entity.setContentEncoding(encoding);
+            }
+            post.setEntity(entity);
+            if (cfg.isCompressionEnabled()) {
+                post.setHeader(ACCEPT_ENCODING, ACCEPT_ENCODING_VAL);
+            }
+        } catch (Exception e) {
+            toThrow = new BOSHException("Could not generate request", e);
+        }
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // HTTPResponse interface methods:
+
+    /**
+     * Abort the client transmission and response processing.
+     */
+    public void abort() {
+        if (post != null) {
+            post.abort();
+            toThrow = new BOSHException("HTTP request aborted");
+        }
+    }
+
+    /**
+     * Wait for and then return the response body.
+     *
+     * @return body of the response
+     * @throws InterruptedException if interrupted while awaiting the response
+     * @throws BOSHException on communication failure
+     */
+    public AbstractBody getBody() throws InterruptedException, BOSHException {
+        if (toThrow != null) {
+            throw(toThrow);
+        }
+        lock.lock();
+        try {
+            if (!sent) {
+                awaitResponse();
+            }
+        } finally {
+            lock.unlock();
+        }
+        return body;
+    }
+
+    /**
+     * Wait for and then return the response HTTP status code.
+     *
+     * @return HTTP status code of the response
+     * @throws InterruptedException if interrupted while awaiting the response
+     * @throws BOSHException on communication failure
+     */
+    public int getHTTPStatus() throws InterruptedException, BOSHException {
+        if (toThrow != null) {
+            throw(toThrow);
+        }
+        lock.lock();
+        try {
+            if (!sent) {
+                awaitResponse();
+            }
+        } finally {
+            lock.unlock();
+        }
+        return statusCode;
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Await the response, storing the result in the instance variables of
+     * this class when they arrive.
+     *
+     * @throws InterruptedException if interrupted while awaiting the response
+     * @throws BOSHException on communication failure
+     */
+    private synchronized void awaitResponse() throws BOSHException {
+        HttpEntity entity = null;
+        try {
+            HttpResponse httpResp = client.execute(post, context);
+            entity = httpResp.getEntity();
+            byte[] data = EntityUtils.toByteArray(entity);
+            String encoding = entity.getContentEncoding() != null ?
+                    entity.getContentEncoding().getValue() :
+                    null;
+            if (ZLIBCodec.getID().equalsIgnoreCase(encoding)) {
+                data = ZLIBCodec.decode(data);
+            } else if (GZIPCodec.getID().equalsIgnoreCase(encoding)) {
+                data = GZIPCodec.decode(data);
+            }
+            body = StaticBody.fromString(new String(data, CHARSET));
+            statusCode = httpResp.getStatusLine().getStatusCode();
+            sent = true;
+        } catch (IOException iox) {
+            abort();
+            toThrow = new BOSHException("Could not obtain response", iox);
+            throw(toThrow);
+        } catch (RuntimeException ex) {
+            abort();
+            throw(ex);
+        }
+    }
+}
diff --git a/src/com/kenai/jbosh/ApacheHTTPSender.java b/src/com/kenai/jbosh/ApacheHTTPSender.java
new file mode 100644
index 0000000..b3d3c93
--- /dev/null
+++ b/src/com/kenai/jbosh/ApacheHTTPSender.java
@@ -0,0 +1,156 @@
+/*
+ * Copyright 2009 Guenther Niess
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+
+import org.apache.http.HttpHost;
+import org.apache.http.HttpVersion;
+import org.apache.http.client.HttpClient;
+import org.apache.http.conn.ClientConnectionManager;
+import org.apache.http.conn.params.ConnManagerParams;
+import org.apache.http.conn.params.ConnRoutePNames;
+import org.apache.http.conn.scheme.PlainSocketFactory;
+import org.apache.http.conn.scheme.Scheme;
+import org.apache.http.conn.scheme.SchemeRegistry;
+import org.apache.http.conn.ssl.SSLSocketFactory;
+import org.apache.http.impl.client.DefaultHttpClient;
+import org.apache.http.impl.conn.tsccm.ThreadSafeClientConnManager;
+import org.apache.http.params.BasicHttpParams;
+import org.apache.http.params.HttpParams;
+import org.apache.http.params.HttpProtocolParams;
+
+/**
+ * Implementation of the {@code HTTPSender} interface which uses the
+ * Apache HttpClient API to send messages to the connection manager.
+ */
+final class ApacheHTTPSender implements HTTPSender {
+
+    /**
+     * Lock used for internal synchronization.
+     */
+    private final Lock lock = new ReentrantLock();
+
+    /**
+     * Session configuration.
+     */
+    private BOSHClientConfig cfg;
+
+    /**
+     * HttpClient instance to use to communicate.
+     */
+    private HttpClient httpClient;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent construction apart from our package.
+     */
+    ApacheHTTPSender() {
+        // Load Apache HTTP client class
+        HttpClient.class.getName();
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // HTTPSender interface methods:
+
+    /**
+     * {@inheritDoc}
+     */
+    public void init(final BOSHClientConfig session) {
+        lock.lock();
+        try {
+            cfg = session;
+            httpClient = initHttpClient(session);
+        } finally {
+            lock.unlock();
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void destroy() {
+        lock.lock();
+        try {
+            if (httpClient != null) {
+                httpClient.getConnectionManager().shutdown();
+            }
+        } finally {
+            cfg = null;
+            httpClient = null;
+            lock.unlock();
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public HTTPResponse send(
+            final CMSessionParams params,
+            final AbstractBody body) {
+        HttpClient mClient;
+        BOSHClientConfig mCfg;
+        lock.lock();
+        try {
+            if (httpClient == null) {
+                httpClient = initHttpClient(cfg);
+            }
+            mClient = httpClient;
+            mCfg = cfg;
+        } finally {
+            lock.unlock();
+        }
+        return new ApacheHTTPResponse(mClient, mCfg, params, body);
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    private synchronized HttpClient initHttpClient(final BOSHClientConfig config) {
+        // Create and initialize HTTP parameters
+        HttpParams params = new BasicHttpParams();
+        ConnManagerParams.setMaxTotalConnections(params, 100);
+        HttpProtocolParams.setVersion(params, HttpVersion.HTTP_1_1);
+        HttpProtocolParams.setUseExpectContinue(params, false);
+        if (config != null &&
+                config.getProxyHost() != null &&
+                config.getProxyPort() != 0) {
+            HttpHost proxy = new HttpHost(
+                    config.getProxyHost(),
+                    config.getProxyPort());
+            params.setParameter(ConnRoutePNames.DEFAULT_PROXY, proxy);
+        }
+
+        // Create and initialize scheme registry 
+        SchemeRegistry schemeRegistry = new SchemeRegistry();
+        schemeRegistry.register(
+                new Scheme("http", PlainSocketFactory.getSocketFactory(), 80));
+            SSLSocketFactory sslFactory = SSLSocketFactory.getSocketFactory();
+            sslFactory.setHostnameVerifier(SSLSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);
+            schemeRegistry.register(
+                    new Scheme("https", sslFactory, 443));
+
+        // Create an HttpClient with the ThreadSafeClientConnManager.
+        // This connection manager must be used if more than one thread will
+        // be using the HttpClient.
+        ClientConnectionManager cm = new ThreadSafeClientConnManager(params, schemeRegistry);
+        return new DefaultHttpClient(cm, params);
+    }
+}
diff --git a/src/com/kenai/jbosh/AttrAccept.java b/src/com/kenai/jbosh/AttrAccept.java
new file mode 100644
index 0000000..4f767df
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrAccept.java
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code accept} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrAccept extends AbstractAttr<String> {
+
+    /**
+     * Array of the accepted encodings.
+     */
+    private final String[] encodings;
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrAccept(final String val) {
+        super(val);
+        encodings = val.split("[\\s,]+");
+    }
+    
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrAccept createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrAccept(str);
+        }
+    }
+
+    /**
+     * Determines whether or not the specified encoding is supported.
+     *
+     * @param name encoding name
+     * @result {@code true} if the encoding is accepted, {@code false}
+     *  otherwise
+     */
+    boolean isAccepted(final String name) {
+        for (String str : encodings) {
+            if (str.equalsIgnoreCase(name)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrAck.java b/src/com/kenai/jbosh/AttrAck.java
new file mode 100644
index 0000000..6cfe22b
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrAck.java
@@ -0,0 +1,52 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code ack} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrAck extends AbstractAttr<String> {
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrAck(final String val) throws BOSHException {
+        super(val);
+    }
+    
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrAck createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrAck(str);
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrCharsets.java b/src/com/kenai/jbosh/AttrCharsets.java
new file mode 100644
index 0000000..45ce78c
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrCharsets.java
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code charsets} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrCharsets extends AbstractAttr<String> {
+
+    /**
+     * Array of the accepted character sets.
+     */
+    private final String[] charsets;
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     */
+    private AttrCharsets(final String val) {
+        super(val);
+        charsets = val.split("\\ +");
+    }
+    
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     */
+    static AttrCharsets createFromString(final String str) {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrCharsets(str);
+        }
+    }
+
+    /**
+     * Determines whether or not the specified charset is supported.
+     *
+     * @param name encoding name
+     * @result {@code true} if the encoding is accepted, {@code false}
+     *  otherwise
+     */
+    boolean isAccepted(final String name) {
+        for (String str : charsets) {
+            if (str.equalsIgnoreCase(name)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrHold.java b/src/com/kenai/jbosh/AttrHold.java
new file mode 100644
index 0000000..56f21dd
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrHold.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code hold} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrHold extends AbstractIntegerAttr {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrHold(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(0);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrHold createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrHold(str);
+        }
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/AttrInactivity.java b/src/com/kenai/jbosh/AttrInactivity.java
new file mode 100644
index 0000000..14ab7d4
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrInactivity.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the value of the {@code inactivity} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrInactivity extends AbstractIntegerAttr {
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute value
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrInactivity(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(0);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return instance of the attribute for the specified string, or
+     *  {@code null} if input string is {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrInactivity createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrInactivity(str);
+        }
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/AttrMaxPause.java b/src/com/kenai/jbosh/AttrMaxPause.java
new file mode 100644
index 0000000..8d1d98b
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrMaxPause.java
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Data type representing the getValue of the {@code maxpause} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrMaxPause extends AbstractIntegerAttr {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrMaxPause(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(1);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrMaxPause createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrMaxPause(str);
+        }
+    }
+    
+    /**
+     * Get the max pause time in milliseconds.
+     *
+     * @return pause tme in milliseconds
+     */
+    public int getInMilliseconds() {
+        return (int) TimeUnit.MILLISECONDS.convert(
+                intValue(), TimeUnit.SECONDS);
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrPause.java b/src/com/kenai/jbosh/AttrPause.java
new file mode 100644
index 0000000..5fb3282
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrPause.java
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Data type representing the getValue of the {@code pause} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrPause extends AbstractIntegerAttr {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrPause(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(1);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrPause createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrPause(str);
+        }
+    }
+    
+    /**
+     * Get the pause time in milliseconds.
+     *
+     * @return pause tme in milliseconds
+     */
+    public int getInMilliseconds() {
+        return (int) TimeUnit.MILLISECONDS.convert(
+                intValue(), TimeUnit.SECONDS);
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrPolling.java b/src/com/kenai/jbosh/AttrPolling.java
new file mode 100644
index 0000000..3f0b08d
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrPolling.java
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.concurrent.TimeUnit;
+
+/**
+ * Data type representing the getValue of the {@code polling} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrPolling extends AbstractIntegerAttr {
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrPolling(final String str) throws BOSHException {
+        super(str);
+        checkMinValue(0);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return instance of the attribute for the specified string, or
+     *  {@code null} if input string is {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrPolling createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrPolling(str);
+        }
+    }
+
+    /**
+     * Get the polling interval in milliseconds.
+     *
+     * @return polling interval in milliseconds
+     */
+    public int getInMilliseconds() {
+        return (int) TimeUnit.MILLISECONDS.convert(
+                intValue(), TimeUnit.SECONDS);
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/AttrRequests.java b/src/com/kenai/jbosh/AttrRequests.java
new file mode 100644
index 0000000..bfdc529
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrRequests.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the value of the {@code requests} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrRequests extends AbstractIntegerAttr {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute value
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrRequests(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(1);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return instance of the attribute for the specified string, or
+     *  {@code null} if input string is {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrRequests createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrRequests(str);
+        }
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/AttrSessionID.java b/src/com/kenai/jbosh/AttrSessionID.java
new file mode 100644
index 0000000..1998968
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrSessionID.java
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code sid} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrSessionID extends AbstractAttr<String> {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     */
+    private AttrSessionID(final String val) {
+        super(val);
+    }
+    
+    /**
+     * Creates a new attribute instance from the provided String.
+     *
+     * @param str string representation of the attribute
+     * @return attribute instance
+     */
+    static AttrSessionID createFromString(final String str) {
+        return new AttrSessionID(str);
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/AttrVersion.java b/src/com/kenai/jbosh/AttrVersion.java
new file mode 100644
index 0000000..9396e3b
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrVersion.java
@@ -0,0 +1,165 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code ver} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrVersion extends AbstractAttr<String> implements Comparable {
+
+    /**
+     * Default value if none is provided.
+     */
+    private static final AttrVersion DEFAULT;
+    static {
+        try {
+            DEFAULT = createFromString("1.8");
+        } catch (BOSHException boshx) {
+            throw(new IllegalStateException(boshx));
+        }
+    }
+
+    /**
+     * Major portion of the version.
+     */
+    private final int major;
+    
+    /**
+     * Minor portion of the version.
+     */
+    private final int minor;
+
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrVersion(final String val) throws BOSHException {
+        super(val);
+
+        int idx = val.indexOf('.');
+        if (idx <= 0) {
+            throw(new BOSHException(
+                    "Illegal ver attribute value (not in major.minor form): "
+                    + val));
+        }
+
+        String majorStr = val.substring(0, idx);
+        try {
+            major = Integer.parseInt(majorStr);
+        } catch (NumberFormatException nfx) {
+            throw(new BOSHException(
+                    "Could not parse ver attribute value (major ver): "
+                    + majorStr,
+                    nfx));
+        }
+        if (major < 0) {
+            throw(new BOSHException(
+                    "Major version may not be < 0"));
+        }
+
+        String minorStr = val.substring(idx + 1);
+        try {
+            minor = Integer.parseInt(minorStr);
+        } catch (NumberFormatException nfx) {
+            throw(new BOSHException(
+                    "Could not parse ver attribute value (minor ver): "
+                    + minorStr,
+                    nfx));
+        }
+        if (minor < 0) {
+            throw(new BOSHException(
+                    "Minor version may not be < 0"));
+        }
+    }
+    
+    /**
+     * Get the version of specifcation that we support.
+     *
+     * @return max spec version the code supports
+     */
+    static AttrVersion getSupportedVersion() {
+        return DEFAULT;
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrVersion createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrVersion(str);
+        }
+    }
+
+    /**
+     * Returns the 'major' portion of the version number.
+     *
+     * @return major digits only
+     */
+    int getMajor() {
+        return major;
+    }
+
+    /**
+     * Returns the 'minor' portion of the version number.
+     *
+     * @return minor digits only
+     */
+    int getMinor() {
+        return minor;
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Comparable interface:
+
+    /**
+     * {@inheritDoc}
+     *
+     * @param otherObj object to compare to
+     * @return -1, 0, or 1
+     */
+    @Override
+    public int compareTo(final Object otherObj) {
+        if (otherObj instanceof AttrVersion) {
+            AttrVersion other = (AttrVersion) otherObj;
+            if (major < other.major) {
+                return -1;
+            } else if (major > other.major) {
+                return 1;
+            } else if (minor < other.minor) {
+                return -1;
+            } else if (minor > other.minor) {
+                return 1;
+            } else {
+                return 0;
+            }
+        } else {
+            return 0;
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/AttrWait.java b/src/com/kenai/jbosh/AttrWait.java
new file mode 100644
index 0000000..d2c95f7
--- /dev/null
+++ b/src/com/kenai/jbosh/AttrWait.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Data type representing the getValue of the {@code wait} attribute of the
+ * {@code bosh} element.
+ */
+final class AttrWait extends AbstractIntegerAttr {
+    
+    /**
+     * Creates a new attribute object.
+     * 
+     * @param val attribute getValue
+     * @throws BOSHException on parse or validation failure
+     */
+    private AttrWait(final String val) throws BOSHException {
+        super(val);
+        checkMinValue(1);
+    }
+
+    /**
+     * Creates a new attribute instance from the provided String.
+     * 
+     * @param str string representation of the attribute
+     * @return attribute instance or {@code null} if provided string is
+     *  {@code null}
+     * @throws BOSHException on parse or validation failure
+     */
+    static AttrWait createFromString(final String str)
+    throws BOSHException {
+        if (str == null) {
+            return null;
+        } else {
+            return new AttrWait(str);
+        }
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/Attributes.java b/src/com/kenai/jbosh/Attributes.java
new file mode 100644
index 0000000..d01541e
--- /dev/null
+++ b/src/com/kenai/jbosh/Attributes.java
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import javax.xml.XMLConstants;
+
+/**
+ * Class containing constants for attribute definitions used by the
+ * XEP-0124 specification.  We shouldn't need to expose these outside
+ * our package, since nobody else should be needing to worry about
+ * them.
+ */
+final class Attributes {
+
+    /**
+     * Private constructor to prevent construction of library class.
+     */
+    private Attributes() {
+        super();
+    }
+
+    static final BodyQName ACCEPT = BodyQName.createBOSH("accept");
+    static final BodyQName AUTHID = BodyQName.createBOSH("authid");
+    static final BodyQName ACK = BodyQName.createBOSH("ack");
+    static final BodyQName CHARSETS = BodyQName.createBOSH("charsets");
+    static final BodyQName CONDITION = BodyQName.createBOSH("condition");
+    static final BodyQName CONTENT = BodyQName.createBOSH("content");
+    static final BodyQName FROM = BodyQName.createBOSH("from");
+    static final BodyQName HOLD = BodyQName.createBOSH("hold");
+    static final BodyQName INACTIVITY = BodyQName.createBOSH("inactivity");
+    static final BodyQName KEY = BodyQName.createBOSH("key");
+    static final BodyQName MAXPAUSE = BodyQName.createBOSH("maxpause");
+    static final BodyQName NEWKEY = BodyQName.createBOSH("newkey");
+    static final BodyQName PAUSE = BodyQName.createBOSH("pause");
+    static final BodyQName POLLING = BodyQName.createBOSH("polling");
+    static final BodyQName REPORT = BodyQName.createBOSH("report");
+    static final BodyQName REQUESTS = BodyQName.createBOSH("requests");
+    static final BodyQName RID = BodyQName.createBOSH("rid");
+    static final BodyQName ROUTE = BodyQName.createBOSH("route");
+    static final BodyQName SECURE = BodyQName.createBOSH("secure");
+    static final BodyQName SID = BodyQName.createBOSH("sid");
+    static final BodyQName STREAM = BodyQName.createBOSH("stream");
+    static final BodyQName TIME = BodyQName.createBOSH("time");
+    static final BodyQName TO = BodyQName.createBOSH("to");
+    static final BodyQName TYPE = BodyQName.createBOSH("type");
+    static final BodyQName VER = BodyQName.createBOSH("ver");
+    static final BodyQName WAIT = BodyQName.createBOSH("wait");
+    static final BodyQName XML_LANG =
+            BodyQName.createWithPrefix(XMLConstants.XML_NS_URI, "lang", "xml");
+}
diff --git a/src/com/kenai/jbosh/BOSHClient.java b/src/com/kenai/jbosh/BOSHClient.java
new file mode 100644
index 0000000..b96d188
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClient.java
@@ -0,0 +1,1536 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import com.kenai.jbosh.ComposableBody.Builder;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Queue;
+import java.util.Set;
+import java.util.SortedSet;
+import java.util.TreeSet;
+import java.util.concurrent.CopyOnWriteArraySet;
+import java.util.concurrent.Executors;
+import java.util.concurrent.RejectedExecutionException;
+import java.util.concurrent.ScheduledExecutorService;
+import java.util.concurrent.ScheduledFuture;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicReference;
+import java.util.concurrent.locks.Condition;
+import java.util.concurrent.locks.ReentrantLock;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+/**
+ * BOSH Client session instance.  Each communication session with a remote
+ * connection manager is represented and handled by an instance of this
+ * class.  This is the main entry point for client-side communications.
+ * To create a new session, a client configuration must first be created
+ * and then used to create a client instance:
+ * <pre>
+ * BOSHClientConfig cfg = BOSHClientConfig.Builder.create(
+ *         "http://server:1234/httpbind", "jabber.org")
+ *     .setFrom("user@jabber.org")
+ *     .build();
+ * BOSHClient client = BOSHClient.create(cfg);
+ * </pre>
+ * Additional client configuration options are available.  See the
+ * {@code BOSHClientConfig.Builder} class for more information.
+ * <p/>
+ * Once a {@code BOSHClient} instance has been created, communication with
+ * the remote connection manager can begin.  No attempt will be made to
+ * establish a connection to the connection manager until the first call
+ * is made to the {@code send(ComposableBody)} method.  Note that it is
+ * possible to send an empty body to cause an immediate connection attempt
+ * to the connection manager.  Sending an empty message would look like
+ * the following:
+ * <pre>
+ * client.send(ComposableBody.builder().build());
+ * </pre>
+ * For more information on creating body messages with content, see the
+ * {@code ComposableBody.Builder} class documentation.
+ * <p/>
+ * Once a session has been successfully started, the client instance can be
+ * used to send arbitrary payload data.  All aspects of the BOSH
+ * protocol involving setting and processing attributes in the BOSH
+ * namespace will be handled by the client code transparently and behind the
+ * scenes.  The user of the client instance can therefore concentrate
+ * entirely on the content of the message payload, leaving the semantics of
+ * the BOSH protocol to the client implementation.
+ * <p/>
+ * To be notified of incoming messages from the remote connection manager,
+ * a {@code BOSHClientResponseListener} should be added to the client instance.
+ * All incoming messages will be published to all response listeners as they
+ * arrive and are processed.  As with the transmission of payload data via
+ * the {@code send(ComposableBody)} method, there is no need to worry about
+ * handling of the BOSH attributes, since this is handled behind the scenes.
+ * <p/>
+ * If the connection to the remote connection manager is terminated (either
+ * explicitly or due to a terminal condition of some sort), all connection
+ * listeners will be notified.  After the connection has been closed, the
+ * client instance is considered dead and a new one must be created in order
+ * to resume communications with the remote server.
+ * <p/>
+ * Instances of this class are thread-safe.
+ *
+ * @see BOSHClientConfig.Builder
+ * @see BOSHClientResponseListener
+ * @see BOSHClientConnListener
+ * @see ComposableBody.Builder
+ */
+public final class BOSHClient {
+
+    /**
+     * Logger.
+     */
+    private static final Logger LOG = Logger.getLogger(
+            BOSHClient.class.getName());
+
+    /**
+     * Value of the 'type' attribute used for session termination.
+     */
+    private static final String TERMINATE = "terminate";
+    
+    /**
+     * Value of the 'type' attribute used for recoverable errors.
+     */
+    private static final String ERROR = "error";
+
+    /**
+     * Message to use for interrupted exceptions.
+     */
+    private static final String INTERRUPTED = "Interrupted";
+
+    /**
+     * Message used for unhandled exceptions.
+     */
+    private static final String UNHANDLED = "Unhandled Exception";
+
+    /**
+     * Message used whena null listener is detected.
+     */
+    private static final String NULL_LISTENER = "Listener may not b enull";
+
+    /**
+     * Default empty request delay.
+     */
+    private static final int DEFAULT_EMPTY_REQUEST_DELAY = 100;
+
+    /**
+     * Amount of time to wait before sending an empty request, in
+     * milliseconds.
+     */
+    private static final int EMPTY_REQUEST_DELAY = Integer.getInteger(
+            BOSHClient.class.getName() + ".emptyRequestDelay",
+            DEFAULT_EMPTY_REQUEST_DELAY);
+
+    /**
+     * Default value for the pause margin.
+     */
+    private static final int DEFAULT_PAUSE_MARGIN = 500;
+
+    /**
+     * The amount of time in milliseconds which will be reserved as a
+     * safety margin when scheduling empty requests against a maxpause
+     * value.   This should give us enough time to build the message
+     * and transport it to the remote host.
+     */
+    private static final int PAUSE_MARGIN = Integer.getInteger(
+            BOSHClient.class.getName() + ".pauseMargin",
+            DEFAULT_PAUSE_MARGIN);
+    
+    /**
+     * Flag indicating whether or not we want to perform assertions.
+     */
+    private static final boolean ASSERTIONS;
+
+    /**
+     * Connection listeners.
+     */
+    private final Set<BOSHClientConnListener> connListeners =
+            new CopyOnWriteArraySet<BOSHClientConnListener>();
+
+    /**
+     * Request listeners.
+     */
+    private final Set<BOSHClientRequestListener> requestListeners =
+            new CopyOnWriteArraySet<BOSHClientRequestListener>();
+
+    /**
+     * Response listeners.
+     */
+    private final Set<BOSHClientResponseListener> responseListeners =
+            new CopyOnWriteArraySet<BOSHClientResponseListener>();
+
+    /**
+     * Lock instance.
+     */
+    private final ReentrantLock lock = new ReentrantLock();
+
+    /**
+     * Condition indicating that there are messages to be exchanged.
+     */
+    private final Condition notEmpty = lock.newCondition();
+
+    /**
+     * Condition indicating that there are available slots for sending
+     * messages.
+     */
+    private final Condition notFull = lock.newCondition();
+
+    /**
+     * Condition indicating that there are no outstanding connections.
+     */
+    private final Condition drained = lock.newCondition();
+
+    /**
+     * Session configuration.
+     */
+    private final BOSHClientConfig cfg;
+
+    /**
+     * Processor thread runnable instance.
+     */
+    private final Runnable procRunnable = new Runnable() {
+        /**
+         * Process incoming messages.
+         */
+        public void run() {
+            processMessages();
+        }
+    };
+
+    /**
+     * Processor thread runnable instance.
+     */
+    private final Runnable emptyRequestRunnable = new Runnable() {
+        /**
+         * Process incoming messages.
+         */
+        public void run() {
+            sendEmptyRequest();
+        }
+    };
+
+    /**
+     * HTTPSender instance.
+     */
+    private final HTTPSender httpSender =
+            new ApacheHTTPSender();
+
+    /**
+     * Storage for test hook implementation.
+     */
+    private final AtomicReference<ExchangeInterceptor> exchInterceptor =
+            new AtomicReference<ExchangeInterceptor>();
+
+    /**
+     * Request ID sequence to use for the session.
+     */
+    private final RequestIDSequence requestIDSeq = new RequestIDSequence();
+
+    /**
+     * ScheduledExcecutor to use for deferred tasks.
+     */
+    private final ScheduledExecutorService schedExec =
+            Executors.newSingleThreadScheduledExecutor();
+
+    /************************************************************
+     * The following vars must be accessed via the lock instance.
+     */
+
+    /**
+     * Thread which is used to process responses from the connection
+     * manager.  Becomes null when session is terminated.
+     */
+    private Thread procThread;
+
+    /**
+     * Future for sending a deferred empty request, if needed.
+     */
+    private ScheduledFuture emptyRequestFuture;
+
+    /**
+     * Connection Manager session parameters.  Only available when in a
+     * connected state.
+     */
+    private CMSessionParams cmParams;
+
+    /**
+     * List of active/outstanding requests.
+     */
+    private Queue<HTTPExchange> exchanges = new LinkedList<HTTPExchange>();
+
+    /**
+     * Set of RIDs which have been received, for the purpose of sending
+     * response acknowledgements.
+     */
+    private SortedSet<Long> pendingResponseAcks = new TreeSet<Long>();
+    
+    /**
+     * The highest RID that we've already received a response for.  This value
+     * is used to implement response acks.
+     */
+    private Long responseAck = Long.valueOf(-1L);
+
+    /**
+     * List of requests which have been made but not yet acknowledged.  This
+     * list remains unpopulated if the CM is not acking requests.
+     */
+    private List<ComposableBody> pendingRequestAcks =
+            new ArrayList<ComposableBody>();
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Classes:
+
+    /**
+     * Class used in testing to dynamically manipulate received exchanges
+     * at test runtime.
+     */
+    abstract static class ExchangeInterceptor {
+        /**
+         * Limit construction.
+         */
+        ExchangeInterceptor() {
+            // Empty;
+        }
+
+        /**
+         * Hook to manipulate an HTTPExchange as is is about to be processed.
+         *
+         * @param exch original exchange that would be processed
+         * @return replacement exchange instance, or {@code null} to skip
+         *  processing of this exchange
+         */
+        abstract HTTPExchange interceptExchange(final HTTPExchange exch);
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Determine whether or not we should perform assertions.  Assertions
+     * can be specified via system property explicitly, or defaulted to
+     * the JVM assertions status.
+     */
+    static {
+        final String prop =
+                BOSHClient.class.getSimpleName() + ".assertionsEnabled";
+        boolean enabled = false;
+        if (System.getProperty(prop) == null) {
+            assert enabled = true;
+        } else {
+            enabled = Boolean.getBoolean(prop);
+        }
+        ASSERTIONS = enabled;
+    }
+
+    /**
+     * Prevent direct construction.
+     */
+    private BOSHClient(final BOSHClientConfig sessCfg) {
+        cfg = sessCfg;
+        init();
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Public methods:
+
+    /**
+     * Create a new BOSH client session using the client configuration
+     * information provided.
+     *
+     * @param clientCfg session configuration
+     * @return BOSH session instance
+     */
+    public static BOSHClient create(final BOSHClientConfig clientCfg) {
+        if (clientCfg == null) {
+            throw(new IllegalArgumentException(
+                    "Client configuration may not be null"));
+        }
+        return new BOSHClient(clientCfg);
+    }
+
+    /**
+     * Get the client configuration that was used to create this client
+     * instance.
+     *
+     * @return client configuration
+     */
+    public BOSHClientConfig getBOSHClientConfig() {
+        return cfg;
+    }
+
+    /**
+     * Adds a connection listener to the session.
+     *
+     * @param listener connection listener to add, if not already added
+     */
+    public void addBOSHClientConnListener(
+            final BOSHClientConnListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        connListeners.add(listener);
+    }
+
+    /**
+     * Removes a connection listener from the session.
+     *
+     * @param listener connection listener to remove, if previously added
+     */
+    public void removeBOSHClientConnListener(
+            final BOSHClientConnListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        connListeners.remove(listener);
+    }
+
+    /**
+     * Adds a request message listener to the session.
+     *
+     * @param listener request listener to add, if not already added
+     */
+    public void addBOSHClientRequestListener(
+            final BOSHClientRequestListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        requestListeners.add(listener);
+    }
+
+    /**
+     * Removes a request message listener from the session, if previously
+     * added.
+     *
+     * @param listener instance to remove
+     */
+    public void removeBOSHClientRequestListener(
+            final BOSHClientRequestListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        requestListeners.remove(listener);
+    }
+
+    /**
+     * Adds a response message listener to the session.
+     *
+     * @param listener response listener to add, if not already added
+     */
+    public void addBOSHClientResponseListener(
+            final BOSHClientResponseListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        responseListeners.add(listener);
+    }
+
+    /**
+     * Removes a response message listener from the session, if previously
+     * added.
+     *
+     * @param listener instance to remove
+     */
+    public void removeBOSHClientResponseListener(
+            final BOSHClientResponseListener listener) {
+        if (listener == null) {
+            throw(new IllegalArgumentException(NULL_LISTENER));
+        }
+        responseListeners.remove(listener);
+    }
+
+    /**
+     * Send the provided message data to the remote connection manager.  The
+     * provided message body does not need to have any BOSH-specific attribute
+     * information set.  It only needs to contain the actual message payload
+     * that should be delivered to the remote server.
+     * <p/>
+     * The first call to this method will result in a connection attempt
+     * to the remote connection manager.  Subsequent calls to this method
+     * will block until the underlying session state allows for the message
+     * to be transmitted.  In certain scenarios - such as when the maximum
+     * number of outbound connections has been reached - calls to this method
+     * will block for short periods of time.
+     *
+     * @param body message data to send to remote server
+     * @throws BOSHException on message transmission failure
+     */
+    public void send(final ComposableBody body) throws BOSHException {
+        assertUnlocked();
+        if (body == null) {
+            throw(new IllegalArgumentException(
+                    "Message body may not be null"));
+        }
+
+        HTTPExchange exch;
+        CMSessionParams params;
+        lock.lock();
+        try {
+            blockUntilSendable(body);
+            if (!isWorking() && !isTermination(body)) {
+                throw(new BOSHException(
+                        "Cannot send message when session is closed"));
+            }
+            
+            long rid = requestIDSeq.getNextRID();
+            ComposableBody request = body;
+            params = cmParams;
+            if (params == null && exchanges.isEmpty()) {
+                // This is the first message being sent
+                request = applySessionCreationRequest(rid, body);
+            } else {
+                request = applySessionData(rid, body);
+                if (cmParams.isAckingRequests()) {
+                    pendingRequestAcks.add(request);
+                }
+            }
+            exch = new HTTPExchange(request);
+            exchanges.add(exch);
+            notEmpty.signalAll();
+            clearEmptyRequest();
+        } finally {
+            lock.unlock();
+        }
+        AbstractBody finalReq = exch.getRequest();
+        HTTPResponse resp = httpSender.send(params, finalReq);
+        exch.setHTTPResponse(resp);
+        fireRequestSent(finalReq);
+    }
+
+    /**
+     * Attempt to pause the current session.  When supported by the remote
+     * connection manager, pausing the session will result in the connection
+     * manager closing out all outstanding requests (including the pause
+     * request) and increases the inactivity timeout of the session.  The
+     * exact value of the temporary timeout is dependent upon the connection
+     * manager.  This method should be used if a client encounters an
+     * exceptional temporary situation during which it will be unable to send
+     * requests to the connection manager for a period of time greater than
+     * the maximum inactivity period.
+     *
+     * The session will revert back to it's normal, unpaused state when the
+     * client sends it's next message.
+     *
+     * @return {@code true} if the connection manager supports session pausing,
+     *  {@code false} if the connection manager does not support session
+     *  pausing or if the session has not yet been established
+     */
+    public boolean pause() {
+        assertUnlocked();
+        lock.lock();
+        AttrMaxPause maxPause = null;
+        try {
+            if (cmParams == null) {
+                return false;
+            }
+
+            maxPause = cmParams.getMaxPause();
+            if (maxPause == null) {
+                return false;
+            }
+        } finally {
+            lock.unlock();
+        }
+        try {
+            send(ComposableBody.builder()
+                    .setAttribute(Attributes.PAUSE, maxPause.toString())
+                    .build());
+        } catch (BOSHException boshx) {
+            LOG.log(Level.FINEST, "Could not send pause", boshx);
+        }
+        return true;
+    }
+
+    /**
+     * End the BOSH session by disconnecting from the remote BOSH connection
+     * manager.
+     *
+     * @throws BOSHException when termination message cannot be sent
+     */
+    public void disconnect() throws BOSHException {
+        disconnect(ComposableBody.builder().build());
+    }
+
+    /**
+     * End the BOSH session by disconnecting from the remote BOSH connection
+     * manager, sending the provided content in the final connection
+     * termination message.
+     *
+     * @param msg final message to send
+     * @throws BOSHException when termination message cannot be sent
+     */
+    public void disconnect(final ComposableBody msg) throws BOSHException {
+        if (msg == null) {
+            throw(new IllegalArgumentException(
+                    "Message body may not be null"));
+        }
+
+        Builder builder = msg.rebuild();
+        builder.setAttribute(Attributes.TYPE, TERMINATE);
+        send(builder.build());
+    }
+
+    /**
+     * Forcibly close this client session instance.  The preferred mechanism
+     * to close the connection is to send a disconnect message and wait for
+     * organic termination.  Calling this method simply shuts down the local
+     * session without sending a termination message, releasing all resources
+     * associated with the session.
+     */
+    public void close() {
+        dispose(new BOSHException("Session explicitly closed by caller"));
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Get the current CM session params.
+     *
+     * @return current session params, or {@code null}
+     */
+    CMSessionParams getCMSessionParams() {
+        lock.lock();
+        try {
+            return cmParams;
+        } finally {
+            lock.unlock();
+        }
+    }
+
+    /**
+     * Wait until no more messages are waiting to be processed.
+     */
+    void drain() {
+        lock.lock();
+        try {
+            LOG.finest("Waiting while draining...");
+            while (isWorking()
+                    && (emptyRequestFuture == null
+                    || emptyRequestFuture.isDone())) {
+                try {
+                    drained.await();
+                } catch (InterruptedException intx) {
+                    LOG.log(Level.FINEST, INTERRUPTED, intx);
+                }
+            }
+            LOG.finest("Drained");
+        } finally {
+            lock.unlock();
+        }
+    }
+
+    /**
+     * Test method used to forcibly discard next exchange.
+     *
+     * @param interceptor exchange interceptor
+     */
+    void setExchangeInterceptor(final ExchangeInterceptor interceptor) {
+        exchInterceptor.set(interceptor);
+    }
+
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Initialize the session.  This initializes the underlying HTTP
+     * transport implementation and starts the receive thread.
+     */
+    private void init() {
+        assertUnlocked();
+        
+        lock.lock();
+        try {
+            httpSender.init(cfg);
+            procThread = new Thread(procRunnable);
+            procThread.setDaemon(true);
+            procThread.setName(BOSHClient.class.getSimpleName()
+                    + "[" + System.identityHashCode(this)
+                    + "]: Receive thread");
+            procThread.start();
+        } finally {
+            lock.unlock();
+        }
+    }
+
+    /**
+     * Destroy this session.
+     *
+     * @param cause the reason for the session termination, or {@code null}
+     *  for normal termination
+     */
+    private void dispose(final Throwable cause) {
+        assertUnlocked();
+        
+        lock.lock();
+        try {
+            if (procThread == null) {
+                // Already disposed
+                return;
+            }
+            procThread = null;
+        } finally {
+            lock.unlock();
+        }
+
+        if (cause == null) {
+            fireConnectionClosed();
+        } else {
+            fireConnectionClosedOnError(cause);
+        }
+
+        lock.lock();
+        try {
+            clearEmptyRequest();
+            exchanges = null;
+            cmParams = null;
+            pendingResponseAcks = null;
+            pendingRequestAcks = null;
+            notEmpty.signalAll();
+            notFull.signalAll();
+            drained.signalAll();
+        } finally {
+            lock.unlock();
+        }
+        
+        httpSender.destroy();
+        schedExec.shutdownNow();
+    }
+
+    /**
+     * Determines if the message body specified indicates a request to
+     * pause the session.
+     *
+     * @param msg message to evaluate
+     * @return {@code true} if the message is a pause request, {@code false}
+     *  otherwise
+     */
+    private static boolean isPause(final AbstractBody msg) {
+        return msg.getAttribute(Attributes.PAUSE) != null;
+    }
+    
+    /**
+     * Determines if the message body specified indicates a termination of
+     * the session.
+     *
+     * @param msg message to evaluate
+     * @return {@code true} if the message is a session termination,
+     *  {@code false} otherwise
+     */
+    private static boolean isTermination(final AbstractBody msg) {
+        return TERMINATE.equals(msg.getAttribute(Attributes.TYPE));
+    }
+
+    /**
+     * Evaluates the HTTP response code and response message and returns the
+     * terminal binding condition that it describes, if any.
+     *
+     * @param respCode HTTP response code
+     * @param respBody response body
+     * @return terminal binding condition, or {@code null} if not a terminal
+     *  binding condition message
+     */
+    private TerminalBindingCondition getTerminalBindingCondition(
+            final int respCode,
+            final AbstractBody respBody) {
+        assertLocked();
+
+        if (isTermination(respBody)) {
+            String str = respBody.getAttribute(Attributes.CONDITION);
+            return TerminalBindingCondition.forString(str);
+        }
+        // Check for deprecated HTTP Error Conditions
+        if (cmParams != null && cmParams.getVersion() == null) {
+            return TerminalBindingCondition.forHTTPResponseCode(respCode);
+        }
+        return null;
+    }
+
+    /**
+     * Determines if the message specified is immediately sendable or if it
+     * needs to block until the session state changes.
+     *
+     * @param msg message to evaluate
+     * @return {@code true} if the message can be immediately sent,
+     *  {@code false} otherwise
+     */
+    private boolean isImmediatelySendable(final AbstractBody msg) {
+        assertLocked();
+
+        if (cmParams == null) {
+            // block if we're waiting for a response to our first request
+            return exchanges.isEmpty();
+        }
+
+        AttrRequests requests = cmParams.getRequests();
+        if (requests == null) {
+            return true;
+        }
+        int maxRequests = requests.intValue();
+        if (exchanges.size() < maxRequests) {
+            return true;
+        }
+        if (exchanges.size() == maxRequests
+                && (isTermination(msg) || isPause(msg))) {
+            // One additional terminate or pause message is allowed
+            return true;
+        }
+        return false;
+    }
+
+    /**
+     * Determines whether or not the session is still active.
+     *
+     * @return {@code true} if it is, {@code false} otherwise
+     */
+    private boolean isWorking() {
+        assertLocked();
+
+        return procThread != null;
+    }
+
+    /**
+     * Blocks until either the message provided becomes immediately
+     * sendable or until the session is terminated.
+     *
+     * @param msg message to evaluate
+     */
+    private void blockUntilSendable(final AbstractBody msg) {
+        assertLocked();
+
+        while (isWorking() && !isImmediatelySendable(msg)) {
+            try {
+                notFull.await();
+            } catch (InterruptedException intx) {
+                LOG.log(Level.FINEST, INTERRUPTED, intx);
+            }
+        }
+    }
+
+    /**
+     * Modifies the specified body message such that it becomes a new
+     * BOSH session creation request.
+     *
+     * @param rid request ID to use
+     * @param orig original body to modify
+     * @return modified message which acts as a session creation request
+     */
+    private ComposableBody applySessionCreationRequest(
+            final long rid, final ComposableBody orig) throws BOSHException {
+        assertLocked();
+        
+        Builder builder = orig.rebuild();
+        builder.setAttribute(Attributes.TO, cfg.getTo());
+        builder.setAttribute(Attributes.XML_LANG, cfg.getLang());
+        builder.setAttribute(Attributes.VER,
+                AttrVersion.getSupportedVersion().toString());
+        builder.setAttribute(Attributes.WAIT, "60");
+        builder.setAttribute(Attributes.HOLD, "1");
+        builder.setAttribute(Attributes.RID, Long.toString(rid));
+        applyRoute(builder);
+        applyFrom(builder);
+        builder.setAttribute(Attributes.ACK, "1");
+
+        // Make sure the following are NOT present (i.e., during retries)
+        builder.setAttribute(Attributes.SID, null);
+        return builder.build();
+    }
+
+    /**
+     * Applies routing information to the request message who's builder has
+     * been provided.
+     *
+     * @param builder builder instance to add routing information to
+     */
+    private void applyRoute(final Builder builder) {
+        assertLocked();
+        
+        String route = cfg.getRoute();
+        if (route != null) {
+            builder.setAttribute(Attributes.ROUTE, route);
+        }
+    }
+
+    /**
+     * Applies the local station ID information to the request message who's
+     * builder has been provided.
+     *
+     * @param builder builder instance to add station ID information to
+     */
+    private void applyFrom(final Builder builder) {
+        assertLocked();
+
+        String from = cfg.getFrom();
+        if (from != null) {
+            builder.setAttribute(Attributes.FROM, from);
+        }
+    }
+
+    /**
+     * Applies existing session data to the outbound request, returning the
+     * modified request.
+     *
+     * This method assumes the lock is currently held.
+     *
+     * @param rid request ID to use
+     * @param orig original/raw request
+     * @return modified request with session information applied
+     */
+    private ComposableBody applySessionData(
+            final long rid,
+            final ComposableBody orig) throws BOSHException {
+        assertLocked();
+
+        Builder builder = orig.rebuild();
+        builder.setAttribute(Attributes.SID,
+                cmParams.getSessionID().toString());
+        builder.setAttribute(Attributes.RID, Long.toString(rid));
+        applyResponseAcknowledgement(builder, rid);
+        return builder.build();
+    }
+
+    /**
+     * Sets the 'ack' attribute of the request to the value of the highest
+     * 'rid' of a request for which it has already received a response in the
+     * case where it has also received all responses associated with lower
+     * 'rid' values.  The only exception is that, after its session creation
+     * request, the client SHOULD NOT include an 'ack' attribute in any request
+     * if it has received responses to all its previous requests.
+     *
+     * @param builder message builder
+     * @param rid current request RID
+     */
+    private void applyResponseAcknowledgement(
+            final Builder builder,
+            final long rid) {
+        assertLocked();
+
+        if (responseAck.equals(Long.valueOf(-1L))) {
+            // We have not received any responses yet
+            return;
+        }
+
+        Long prevRID = Long.valueOf(rid - 1L);
+        if (responseAck.equals(prevRID)) {
+            // Implicit ack
+            return;
+        }
+        
+        builder.setAttribute(Attributes.ACK, responseAck.toString());
+    }
+
+    /**
+     * While we are "connected", process received responses.
+     *
+     * This method is run in the processing thread.
+     */
+    private void processMessages() {
+        LOG.log(Level.FINEST, "Processing thread starting");
+        try {
+            HTTPExchange exch;
+            do {
+                exch = nextExchange();
+                if (exch == null) {
+                    break;
+                }
+
+                // Test hook to manipulate what the client sees:
+                ExchangeInterceptor interceptor = exchInterceptor.get();
+                if (interceptor != null) {
+                    HTTPExchange newExch = interceptor.interceptExchange(exch);
+                    if (newExch == null) {
+                        LOG.log(Level.FINE, "Discarding exchange on request "
+                                + "of test hook: RID="
+                                + exch.getRequest().getAttribute(
+                                    Attributes.RID));
+                        lock.lock();
+                        try {
+                            exchanges.remove(exch);
+                        } finally {
+                            lock.unlock();
+                        }
+                        continue;
+                    }
+                    exch = newExch;
+                }
+
+                processExchange(exch);
+            } while (true);
+        } finally {
+            LOG.log(Level.FINEST, "Processing thread exiting");
+        }
+
+    }
+
+    /**
+     * Get the next message exchange to process, blocking until one becomes
+     * available if nothing is already waiting for processing.
+     *
+     * @return next available exchange to process, or {@code null} if no
+     *  exchanges are immediately available
+     */
+    private HTTPExchange nextExchange() {
+        assertUnlocked();
+
+        final Thread thread = Thread.currentThread();
+        HTTPExchange exch = null;
+        lock.lock();
+        try {
+            do {
+                if (!thread.equals(procThread)) {
+                    break;
+                }
+                exch = exchanges.peek();
+                if (exch == null) {
+                    try {
+                        notEmpty.await();
+                    } catch (InterruptedException intx) {
+                        LOG.log(Level.FINEST, INTERRUPTED, intx);
+                    }
+                }
+            } while (exch == null);
+        } finally {
+            lock.unlock();
+        }
+        return exch;
+    }
+
+    /**
+     * Process the next, provided exchange.  This is the main processing
+     * method of the receive thread.
+     *
+     * @param exch message exchange to process
+     */
+    private void processExchange(final HTTPExchange exch) {
+        assertUnlocked();
+
+        HTTPResponse resp;
+        AbstractBody body;
+        int respCode;
+        try {
+            resp = exch.getHTTPResponse();
+            body = resp.getBody();
+            respCode = resp.getHTTPStatus();
+        } catch (BOSHException boshx) {
+            LOG.log(Level.FINEST, "Could not obtain response", boshx);
+            dispose(boshx);
+            return;
+        } catch (InterruptedException intx) {
+            LOG.log(Level.FINEST, INTERRUPTED, intx);
+            dispose(intx);
+            return;
+        }
+        fireResponseReceived(body);
+
+        // Process the message with the current session state
+        AbstractBody req = exch.getRequest();
+        CMSessionParams params;
+        List<HTTPExchange> toResend = null;
+        lock.lock();
+        try {
+            // Check for session creation response info, if needed
+            if (cmParams == null) {
+                cmParams = CMSessionParams.fromSessionInit(req, body);
+
+                // The following call handles the lock. It's not an escape.
+                fireConnectionEstablished();
+            }
+            params = cmParams;
+
+            checkForTerminalBindingConditions(body, respCode);
+            if (isTermination(body)) {
+                // Explicit termination
+                lock.unlock();
+                dispose(null);
+                return;
+            }
+            
+            if (isRecoverableBindingCondition(body)) {
+                // Retransmit outstanding requests
+                if (toResend == null) {
+                    toResend = new ArrayList<HTTPExchange>(exchanges.size());
+                }
+                for (HTTPExchange exchange : exchanges) {
+                    HTTPExchange resendExch =
+                            new HTTPExchange(exchange.getRequest());
+                    toResend.add(resendExch);
+                }
+                for (HTTPExchange exchange : toResend) {
+                    exchanges.add(exchange);
+                }
+            } else {
+                // Process message as normal
+                processRequestAcknowledgements(req, body);
+                processResponseAcknowledgementData(req);
+                HTTPExchange resendExch =
+                        processResponseAcknowledgementReport(body);
+                if (resendExch != null && toResend == null) {
+                    toResend = new ArrayList<HTTPExchange>(1);
+                    toResend.add(resendExch);
+                    exchanges.add(resendExch);
+                }
+            }
+        } catch (BOSHException boshx) {
+            LOG.log(Level.FINEST, "Could not process response", boshx);
+            lock.unlock();
+            dispose(boshx);
+            return;
+        } finally {
+            if (lock.isHeldByCurrentThread()) {
+                try {
+                    exchanges.remove(exch);
+                    if (exchanges.isEmpty()) {
+                        scheduleEmptyRequest(processPauseRequest(req));
+                    }
+                    notFull.signalAll();
+                } finally {
+                    lock.unlock();
+                }
+            }
+        }
+
+        if (toResend != null) {
+            for (HTTPExchange resend : toResend) {
+                HTTPResponse response =
+                        httpSender.send(params, resend.getRequest());
+                resend.setHTTPResponse(response);
+                fireRequestSent(resend.getRequest());
+            }
+        }
+    }
+    
+    /**
+     * Clears any scheduled empty requests.
+     */
+    private void clearEmptyRequest() {
+        assertLocked();
+
+        if (emptyRequestFuture != null) {
+            emptyRequestFuture.cancel(false);
+            emptyRequestFuture = null;
+        }
+    }
+
+    /**
+     * Calculates the default empty request delay/interval to use for the
+     * active session.
+     *
+     * @return delay in milliseconds
+     */
+    private long getDefaultEmptyRequestDelay() {
+        assertLocked();
+        
+        // Figure out how long we should wait before sending an empty request
+        AttrPolling polling = cmParams.getPollingInterval();
+        long delay;
+        if (polling == null) {
+            delay = EMPTY_REQUEST_DELAY;
+        } else {
+            delay = polling.getInMilliseconds();
+        }
+        return delay;
+    }
+
+    /**
+     * Schedule an empty request to be sent if no other requests are
+     * sent in a reasonable amount of time.
+     */
+    private void scheduleEmptyRequest(long delay) {
+        assertLocked();
+        if (delay < 0L) {
+            throw(new IllegalArgumentException(
+                    "Empty request delay must be >= 0 (was: " + delay + ")"));
+        }
+
+        clearEmptyRequest();
+        if (!isWorking()) {
+            return;
+        }
+        
+        // Schedule the transmission
+        if (LOG.isLoggable(Level.FINER)) {
+            LOG.finer("Scheduling empty request in " + delay + "ms");
+        }
+        try {
+            emptyRequestFuture = schedExec.schedule(emptyRequestRunnable,
+                    delay, TimeUnit.MILLISECONDS);
+        } catch (RejectedExecutionException rex) {
+            LOG.log(Level.FINEST, "Could not schedule empty request", rex);
+        }
+        drained.signalAll();
+    }
+
+    /**
+     * Sends an empty request to maintain session requirements.  If a request
+     * is sent within a reasonable time window, the empty request transmission
+     * will be cancelled.
+     */
+    private void sendEmptyRequest() {
+        assertUnlocked();
+        // Send an empty request
+        LOG.finest("Sending empty request");
+        try {
+            send(ComposableBody.builder().build());
+        } catch (BOSHException boshx) {
+            dispose(boshx);
+        }
+    }
+
+    /**
+     * Assert that the internal lock is held.
+     */
+    private void assertLocked() {
+        if (ASSERTIONS) {
+            if (!lock.isHeldByCurrentThread()) {
+                throw(new AssertionError("Lock is not held by current thread"));
+            }
+            return;
+        }
+    }
+
+    /**
+     * Assert that the internal lock is *not* held.
+     */
+    private void assertUnlocked() {
+        if (ASSERTIONS) {
+            if (lock.isHeldByCurrentThread()) {
+                throw(new AssertionError("Lock is held by current thread"));
+            }
+            return;
+        }
+    }
+
+    /**
+     * Checks to see if the response indicates a terminal binding condition
+     * (as per XEP-0124 section 17).  If it does, an exception is thrown.
+     *
+     * @param body response body to evaluate
+     * @param code HTTP response code
+     * @throws BOSHException if a terminal binding condition is detected
+     */
+    private void checkForTerminalBindingConditions(
+            final AbstractBody body,
+            final int code)
+            throws BOSHException {
+        TerminalBindingCondition cond =
+                getTerminalBindingCondition(code, body);
+        if (cond != null) {
+            throw(new BOSHException(
+                    "Terminal binding condition encountered: "
+                    + cond.getCondition() + "  ("
+                    + cond.getMessage() + ")"));
+        }
+    }
+
+    /**
+     * Determines whether or not the response indicates a recoverable
+     * binding condition (as per XEP-0124 section 17).
+     *
+     * @param resp response body
+     * @return {@code true} if it does, {@code false} otherwise
+     */
+    private static boolean isRecoverableBindingCondition(
+            final AbstractBody resp) {
+        return ERROR.equals(resp.getAttribute(Attributes.TYPE));
+    }
+
+    /**
+     * Process the request to determine if the empty request delay
+     * can be determined by looking to see if the request is a pause
+     * request.  If it can, the request's delay is returned, otherwise
+     * the default delay is returned.
+     * 
+     * @return delay in milliseconds that should elapse prior to an
+     *  empty message being sent
+     */
+    private long processPauseRequest(
+            final AbstractBody req) {
+        assertLocked();
+
+        if (cmParams != null && cmParams.getMaxPause() != null) {
+            try {
+                AttrPause pause = AttrPause.createFromString(
+                        req.getAttribute(Attributes.PAUSE));
+                if (pause != null) {
+                    long delay = pause.getInMilliseconds() - PAUSE_MARGIN;
+                    if (delay < 0) {
+                        delay = EMPTY_REQUEST_DELAY;
+                    }
+                    return delay;
+                }
+            } catch (BOSHException boshx) {
+                LOG.log(Level.FINEST, "Could not extract", boshx);
+            }
+        }
+
+        return getDefaultEmptyRequestDelay();
+    }
+
+    /**
+     * Check the response for request acknowledgements and take appropriate
+     * action.
+     *
+     * This method assumes the lock is currently held.
+     *
+     * @param req request
+     * @param resp response
+     */
+    private void processRequestAcknowledgements(
+            final AbstractBody req, final AbstractBody resp) {
+        assertLocked();
+        
+        if (!cmParams.isAckingRequests()) {
+            return;
+        }
+
+        // If a report or time attribute is set, we aren't acking anything
+        if (resp.getAttribute(Attributes.REPORT) != null) {
+            return;
+        }
+
+        // Figure out what the highest acked RID is
+        String acked = resp.getAttribute(Attributes.ACK);
+        Long ackUpTo;
+        if (acked == null) {
+            // Implicit ack of all prior requests up until RID
+            ackUpTo = Long.parseLong(req.getAttribute(Attributes.RID));
+        } else {
+            ackUpTo = Long.parseLong(acked);
+        }
+
+        // Remove the acked requests from the list
+        if (LOG.isLoggable(Level.FINEST)) {
+            LOG.finest("Removing pending acks up to: " + ackUpTo);
+        }
+        Iterator<ComposableBody> iter = pendingRequestAcks.iterator();
+        while (iter.hasNext()) {
+            AbstractBody pending = iter.next();
+            Long pendingRID = Long.parseLong(
+                    pending.getAttribute(Attributes.RID));
+            if (pendingRID.compareTo(ackUpTo) <= 0) {
+                iter.remove();
+            }
+        }
+    }
+
+    /**
+     * Process the response in order to update the response acknowlegement
+     * data.
+     *
+     * This method assumes the lock is currently held.
+     *
+     * @param req request
+     */
+    private void processResponseAcknowledgementData(
+            final AbstractBody req) {
+        assertLocked();
+        
+        Long rid = Long.parseLong(req.getAttribute(Attributes.RID));
+        if (responseAck.equals(Long.valueOf(-1L))) {
+            // This is the first request
+            responseAck = rid;
+        } else {
+            pendingResponseAcks.add(rid);
+            // Remove up until the first missing response (or end of queue)
+            Long whileVal = responseAck;
+            while (whileVal.equals(pendingResponseAcks.first())) {
+                responseAck = whileVal;
+                pendingResponseAcks.remove(whileVal);
+                whileVal = Long.valueOf(whileVal.longValue() + 1);
+            }
+        }
+    }
+
+    /**
+     * Process the response in order to check for and respond to any potential
+     * ack reports.
+     *
+     * This method assumes the lock is currently held.
+     *
+     * @param resp response
+     * @return exchange to transmit if a resend is to be performed, or
+     *  {@code null} if no resend is necessary
+     * @throws BOSHException when a a retry is needed but cannot be performed
+     */
+    private HTTPExchange processResponseAcknowledgementReport(
+            final AbstractBody resp)
+            throws BOSHException {
+        assertLocked();
+        
+        String reportStr = resp.getAttribute(Attributes.REPORT);
+        if (reportStr == null) {
+            // No report on this message
+            return null;
+        }
+        
+        Long report = Long.parseLong(reportStr);
+        Long time = Long.parseLong(resp.getAttribute(Attributes.TIME));
+        if (LOG.isLoggable(Level.FINE)) {
+            LOG.fine("Received report of missing request (RID="
+                    + report + ", time=" + time + "ms)");
+        }
+
+        // Find the missing request
+        Iterator<ComposableBody> iter = pendingRequestAcks.iterator();
+        AbstractBody req = null;
+        while (iter.hasNext() && req == null) {
+            AbstractBody pending = iter.next();
+            Long pendingRID = Long.parseLong(
+                    pending.getAttribute(Attributes.RID));
+            if (report.equals(pendingRID)) {
+                req = pending;
+            }
+        }
+
+        if (req == null) {
+            throw(new BOSHException("Report of missing message with RID '"
+                    + reportStr
+                    + "' but local copy of that request was not found"));
+        }
+
+        // Resend the missing request
+        HTTPExchange exch = new HTTPExchange(req);
+        exchanges.add(exch);
+        notEmpty.signalAll();
+        return exch;
+    }
+
+    /**
+     * Notifies all request listeners that the specified request is being
+     * sent.
+     *
+     * @param request request being sent
+     */
+    private void fireRequestSent(final AbstractBody request) {
+        assertUnlocked();
+
+        BOSHMessageEvent event = null;
+        for (BOSHClientRequestListener listener : requestListeners) {
+            if (event == null) {
+                event = BOSHMessageEvent.createRequestSentEvent(this, request);
+            }
+            try {
+                listener.requestSent(event);
+            } catch (Exception ex) {
+                LOG.log(Level.WARNING, UNHANDLED, ex);
+            }
+        }
+    }
+
+    /**
+     * Notifies all response listeners that the specified response has been
+     * received.
+     *
+     * @param response response received
+     */
+    private void fireResponseReceived(final AbstractBody response) {
+        assertUnlocked();
+
+        BOSHMessageEvent event = null;
+        for (BOSHClientResponseListener listener : responseListeners) {
+            if (event == null) {
+                event = BOSHMessageEvent.createResponseReceivedEvent(
+                        this, response);
+            }
+            try {
+                listener.responseReceived(event);
+            } catch (Exception ex) {
+                LOG.log(Level.WARNING, UNHANDLED, ex);
+            }
+        }
+    }
+
+    /**
+     * Notifies all connection listeners that the session has been successfully
+     * established.
+     */
+    private void fireConnectionEstablished() {
+        final boolean hadLock = lock.isHeldByCurrentThread();
+        if (hadLock) {
+            lock.unlock();
+        }
+        try {
+            BOSHClientConnEvent event = null;
+            for (BOSHClientConnListener listener : connListeners) {
+                if (event == null) {
+                    event = BOSHClientConnEvent
+                            .createConnectionEstablishedEvent(this);
+                }
+                try {
+                    listener.connectionEvent(event);
+                } catch (Exception ex) {
+                    LOG.log(Level.WARNING, UNHANDLED, ex);
+                }
+            }
+        } finally {
+            if (hadLock) {
+                lock.lock();
+            }
+        }
+    }
+
+    /**
+     * Notifies all connection listeners that the session has been
+     * terminated normally.
+     */
+    private void fireConnectionClosed() {
+        assertUnlocked();
+
+        BOSHClientConnEvent event = null;
+        for (BOSHClientConnListener listener : connListeners) {
+            if (event == null) {
+                event = BOSHClientConnEvent.createConnectionClosedEvent(this);
+            }
+            try {
+                listener.connectionEvent(event);
+            } catch (Exception ex) {
+                LOG.log(Level.WARNING, UNHANDLED, ex);
+            }
+        }
+    }
+
+    /**
+     * Notifies all connection listeners that the session has been
+     * terminated due to the exceptional condition provided.
+     *
+     * @param cause cause of the termination
+     */
+    private void fireConnectionClosedOnError(
+            final Throwable cause) {
+        assertUnlocked();
+
+        BOSHClientConnEvent event = null;
+        for (BOSHClientConnListener listener : connListeners) {
+            if (event == null) {
+                event = BOSHClientConnEvent
+                        .createConnectionClosedOnErrorEvent(
+                        this, pendingRequestAcks, cause);
+            }
+            try {
+                listener.connectionEvent(event);
+            } catch (Exception ex) {
+                LOG.log(Level.WARNING, UNHANDLED, ex);
+            }
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/BOSHClientConfig.java b/src/com/kenai/jbosh/BOSHClientConfig.java
new file mode 100644
index 0000000..23915b6
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClientConfig.java
@@ -0,0 +1,446 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.net.URI;
+import javax.net.ssl.SSLContext;
+
+/**
+ * BOSH client configuration information.  Instances of this class contain
+ * all information necessary to establish connectivity with a remote
+ * connection manager.
+ * <p/>
+ * Instances of this class are immutable, thread-safe,
+ * and can be re-used to configure multiple client session instances.
+ */
+public final class BOSHClientConfig {
+
+    /**
+     * Connection manager URI.
+     */
+    private final URI uri;
+
+    /**
+     * Target domain.
+     */
+    private final String to;
+
+    /**
+     * Client ID of this station.
+     */
+    private final String from;
+
+    /**
+     * Default XML language.
+     */
+    private final String lang;
+
+    /**
+     * Routing information for messages sent to CM.
+     */
+    private final String route;
+
+    /**
+     * Proxy host.
+     */
+    private final String proxyHost;
+
+    /**
+     * Proxy port.
+     */
+    private final int proxyPort;
+
+    /**
+     * SSL context.
+     */
+    private final SSLContext sslContext;
+
+    /**
+     * Flag indicating that compression should be attempted, if possible.
+     */
+    private final boolean compressionEnabled;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Classes:
+
+    /**
+     * Class instance builder, after the builder pattern.  This allows each
+     * {@code BOSHClientConfig} instance to be immutable while providing
+     * flexibility when building new {@code BOSHClientConfig} instances.
+     * <p/>
+     * Instances of this class are <b>not</b> thread-safe.  If template-style
+     * use is desired, see the {@code create(BOSHClientConfig)} method.
+     */
+    public static final class Builder {
+        // Required args
+        private final URI bURI;
+        private final String bDomain;
+
+        // Optional args
+        private String bFrom;
+        private String bLang;
+        private String bRoute;
+        private String bProxyHost;
+        private int bProxyPort;
+        private SSLContext bSSLContext;
+        private Boolean bCompression;
+
+        /**
+         * Creates a new builder instance, used to create instances of the
+         * {@code BOSHClientConfig} class.
+         *
+         * @param cmURI URI to use to contact the connection manager
+         * @param domain target domain to communicate with
+         */
+        private Builder(final URI cmURI, final String domain) {
+            bURI = cmURI;
+            bDomain = domain;
+        }
+
+        /**
+         * Creates a new builder instance, used to create instances of the
+         * {@code BOSHClientConfig} class.
+         *
+         * @param cmURI URI to use to contact the connection manager
+         * @param domain target domain to communicate with
+         * @return builder instance
+         */
+        public static Builder create(final URI cmURI, final String domain) {
+            if (cmURI == null) {
+                throw(new IllegalArgumentException(
+                        "Connection manager URI must not be null"));
+            }
+            if (domain == null) {
+                throw(new IllegalArgumentException(
+                        "Target domain must not be null"));
+            }
+            String scheme = cmURI.getScheme();
+            if (!("http".equals(scheme) || "https".equals(scheme))) {
+                throw(new IllegalArgumentException(
+                        "Only 'http' and 'https' URI are allowed"));
+            }
+            return new Builder(cmURI, domain);
+        }
+
+        /**
+         * Creates a new builder instance using the existing configuration
+         * provided as a starting point.
+         *
+         * @param cfg configuration to copy
+         * @return builder instance
+         */
+        public static Builder create(final BOSHClientConfig cfg) {
+            Builder result = new Builder(cfg.getURI(), cfg.getTo());
+            result.bFrom = cfg.getFrom();
+            result.bLang = cfg.getLang();
+            result.bRoute = cfg.getRoute();
+            result.bProxyHost = cfg.getProxyHost();
+            result.bProxyPort = cfg.getProxyPort();
+            result.bSSLContext = cfg.getSSLContext();
+            result.bCompression = cfg.isCompressionEnabled();
+            return result;
+        }
+
+        /**
+         * Set the ID of the client station, to be forwarded to the connection
+         * manager when new sessions are created.
+         *
+         * @param id client ID
+         * @return builder instance
+         */
+        public Builder setFrom(final String id) {
+            if (id == null) {
+                throw(new IllegalArgumentException(
+                        "Client ID must not be null"));
+            }
+            bFrom = id;
+            return this;
+        }
+        
+        /**
+         * Set the default language of any human-readable content within the
+         * XML.
+         *
+         * @param lang XML language ID
+         * @return builder instance
+         */
+        public Builder setXMLLang(final String lang) {
+            if (lang == null) {
+                throw(new IllegalArgumentException(
+                        "Default language ID must not be null"));
+            }
+            bLang = lang;
+            return this;
+        }
+
+        /**
+         * Sets the destination server/domain that the client should connect to.
+         * Connection managers may be configured to enable sessions with more
+         * that one server in different domains.  When requesting a session with
+         * such a "proxy" connection manager, a client should use this method to
+         * specify the server with which it wants to communicate.
+         *
+         * @param protocol connection protocol (e.g, "xmpp")
+         * @param host host or domain to be served by the remote server.  Note
+         *  that this is not necessarily the host name or domain name of the
+         *  remote server.
+         * @param port port number of the remote server
+         * @return builder instance
+         */
+        public Builder setRoute(
+                final String protocol,
+                final String host,
+                final int port) {
+            if (protocol == null) {
+                throw(new IllegalArgumentException("Protocol cannot be null"));
+            }
+            if (protocol.contains(":")) {
+                throw(new IllegalArgumentException(
+                        "Protocol cannot contain the ':' character"));
+            }
+            if (host == null) {
+                throw(new IllegalArgumentException("Host cannot be null"));
+            }
+            if (host.contains(":")) {
+                throw(new IllegalArgumentException(
+                        "Host cannot contain the ':' character"));
+            }
+            if (port <= 0) {
+                throw(new IllegalArgumentException("Port number must be > 0"));
+            }
+            bRoute = protocol + ":" + host + ":" + port;
+            return this;
+        }
+
+        /**
+         * Specify the hostname and port of an HTTP proxy to connect through.
+         *
+         * @param hostName proxy hostname
+         * @param port proxy port number
+         * @return builder instance
+         */
+        public Builder setProxy(final String hostName, final int port) {
+            if (hostName == null || hostName.length() == 0) {
+                throw(new IllegalArgumentException(
+                        "Proxy host name cannot be null or empty"));
+            }
+            if (port <= 0) {
+                throw(new IllegalArgumentException(
+                        "Proxy port must be > 0"));
+            }
+            bProxyHost = hostName;
+            bProxyPort = port;
+            return this;
+        }
+
+        /**
+         * Set the SSL context to use for this session.  This can be used
+         * to configure certificate-based authentication, etc..
+         *
+         * @param ctx SSL context
+         * @return builder instance
+         */
+        public Builder setSSLContext(final SSLContext ctx) {
+            if (ctx == null) {
+                throw(new IllegalArgumentException(
+                        "SSL context cannot be null"));
+            }
+            bSSLContext = ctx;
+            return this;
+        }
+
+        /**
+         * Set whether or not compression of the underlying data stream
+         * should be attempted.  By default, compression is disabled.
+         *
+         * @param enabled set to {@code true} if compression should be
+         *  attempted when possible, {@code false} to disable compression
+         * @return builder instance
+         */
+        public Builder setCompressionEnabled(final boolean enabled) {
+            bCompression = Boolean.valueOf(enabled);
+            return this;
+        }
+
+        /**
+         * Build the immutable object instance with the current configuration.
+         *
+         * @return BOSHClientConfig instance
+         */
+        public BOSHClientConfig build() {
+            // Default XML language
+            String lang;
+            if (bLang == null) {
+                lang = "en";
+            } else {
+                lang = bLang;
+            }
+
+            // Default proxy port
+            int port;
+            if (bProxyHost == null) {
+                port = 0;
+            } else {
+                port = bProxyPort;
+            }
+
+            // Default compression
+            boolean compression;
+            if (bCompression == null) {
+                compression = false;
+            } else {
+                compression = bCompression.booleanValue();
+            }
+
+            return new BOSHClientConfig(
+                    bURI,
+                    bDomain,
+                    bFrom,
+                    lang,
+                    bRoute,
+                    bProxyHost,
+                    port,
+                    bSSLContext,
+                    compression);
+        }
+
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructor:
+
+    /**
+     * Prevent direct construction.
+     *
+     * @param cURI URI of the connection manager to connect to
+     * @param cDomain the target domain of the first stream
+     * @param cFrom client ID
+     * @param cLang default XML language
+     * @param cRoute target route
+     * @param cProxyHost proxy host
+     * @param cProxyPort proxy port
+     * @param cSSLContext SSL context
+     * @param cCompression compression enabled flag
+     */
+    private BOSHClientConfig(
+            final URI cURI,
+            final String cDomain,
+            final String cFrom,
+            final String cLang,
+            final String cRoute,
+            final String cProxyHost,
+            final int cProxyPort,
+            final SSLContext cSSLContext,
+            final boolean cCompression) {
+        uri = cURI;
+        to = cDomain;
+        from = cFrom;
+        lang = cLang;
+        route = cRoute;
+        proxyHost = cProxyHost;
+        proxyPort = cProxyPort;
+        sslContext = cSSLContext;
+        compressionEnabled = cCompression;
+    }
+
+    /**
+     * Get the URI to use to contact the connection manager.
+     *
+     * @return connection manager URI.
+     */
+    public URI getURI() {
+        return uri;
+    }
+
+    /**
+     * Get the ID of the target domain.
+     *
+     * @return domain id
+     */
+    public String getTo() {
+        return to;
+    }
+
+    /**
+     * Get the ID of the local client.
+     *
+     * @return client id, or {@code null}
+     */
+    public String getFrom() {
+        return from;
+    }
+
+    /**
+     * Get the default language of any human-readable content within the
+     * XML.  Defaults to "en".
+     *
+     * @return XML language ID
+     */
+    public String getLang() {
+        return lang;
+    }
+
+    /**
+     * Get the routing information for messages sent to the CM.
+     *
+     * @return route attribute string, or {@code null} if no routing
+     *  info was provided.
+     */
+    public String getRoute() {
+        return route;
+    }
+
+    /**
+     * Get the HTTP proxy host to use.
+     *
+     * @return proxy host, or {@code null} if no proxy information was specified
+     */
+    public String getProxyHost() {
+        return proxyHost;
+    }
+
+    /**
+     * Get the HTTP proxy port to use.
+     *
+     * @return proxy port, or 0 if no proxy information was specified
+     */
+    public int getProxyPort() {
+        return proxyPort;
+    }
+
+    /**
+     * Get the SSL context to use for this session.
+     *
+     * @return SSL context instance to use, or {@code null} if no
+     *  context instance was provided.
+     */
+    public SSLContext getSSLContext() {
+        return sslContext;
+    }
+
+    /**
+     * Determines whether or not compression of the underlying data stream
+     * should be attempted/allowed.  Defaults to {@code false}.
+     *
+     * @return {@code true} if compression should be attempted, {@code false}
+     *  if compression is disabled or was not specified
+     */
+    boolean isCompressionEnabled() {
+        return compressionEnabled;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/BOSHClientConnEvent.java b/src/com/kenai/jbosh/BOSHClientConnEvent.java
new file mode 100644
index 0000000..0ac7943
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClientConnEvent.java
@@ -0,0 +1,189 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.EventObject;
+import java.util.List;
+
+/**
+ * Client connection event, notifying of changes in connection state.
+ * <p/>
+ * This class is immutable and thread-safe.
+ */
+public final class BOSHClientConnEvent extends EventObject {
+
+    /**
+     * Serialized version.
+     */
+    private static final long serialVersionUID = 1L;
+    
+    /**
+     * Boolean flag indicating whether or not a session has been established
+     * and is currently active.
+     */
+    private final boolean connected;
+
+    /**
+     * List of outstanding requests which may not have been sent and/or
+     * acknowledged by the remote CM.
+     */
+    private final List<ComposableBody> requests;
+
+    /**
+     * Cause of the session termination, or {@code null}.
+     */
+    private final Throwable cause;
+
+    /**
+     * Creates a new connection event instance.
+     *
+     * @param source event source
+     * @param cConnected flag indicating whether or not the session is
+     *  currently active
+     * @param cRequests outstanding requests when an error condition is
+     *  detected, or {@code null} when not an error condition
+     * @param cCause cause of the error condition, or {@code null} when no
+     *  error condition is present
+     */
+    private BOSHClientConnEvent(
+            final BOSHClient source,
+            final boolean cConnected,
+            final List<ComposableBody> cRequests,
+            final Throwable cCause) {
+        super(source);
+        connected = cConnected;
+        cause = cCause;
+
+        if (connected) {
+            if (cCause != null) {
+                throw(new IllegalStateException(
+                        "Cannot be connected and have a cause"));
+            }
+            if (cRequests != null && cRequests.size() > 0) {
+                throw(new IllegalStateException(
+                        "Cannot be connected and have outstanding requests"));
+            }
+        }
+
+        if (cRequests == null) {
+            requests = Collections.emptyList();
+        } else {
+            // Defensive copy:
+            requests = Collections.unmodifiableList(
+                    new ArrayList<ComposableBody>(cRequests));
+        }
+    }
+
+    /**
+     * Creates a new connection establishment event.
+     *
+     * @param source client which has become connected
+     * @return event instance
+     */
+    static BOSHClientConnEvent createConnectionEstablishedEvent(
+            final BOSHClient source) {
+        return new BOSHClientConnEvent(source, true, null, null);
+    }
+
+    /**
+     * Creates a new successful connection closed event.  This represents
+     * a clean termination of the client session.
+     *
+     * @param source client which has been disconnected
+     * @return event instance
+     */
+    static BOSHClientConnEvent createConnectionClosedEvent(
+            final BOSHClient source) {
+        return new BOSHClientConnEvent(source, false, null, null);
+    }
+
+    /**
+     * Creates a connection closed on error event.  This represents
+     * an unexpected termination of the client session.
+     *
+     * @param source client which has been disconnected
+     * @param outstanding list of requests which may not have been received
+     *  by the remote connection manager
+     * @param cause cause of termination
+     * @return event instance
+     */
+    static BOSHClientConnEvent createConnectionClosedOnErrorEvent(
+            final BOSHClient source,
+            final List<ComposableBody> outstanding,
+            final Throwable cause) {
+        return new BOSHClientConnEvent(source, false, outstanding, cause);
+    }
+
+    /**
+     * Gets the client from which this event originated.
+     *
+     * @return client instance
+     */
+    public BOSHClient getBOSHClient() {
+        return (BOSHClient) getSource();
+    }
+
+    /**
+     * Returns whether or not the session has been successfully established
+     * and is currently active.
+     *
+     * @return {@code true} if a session is active, {@code false} otherwise
+     */
+    public boolean isConnected() {
+        return connected;
+    }
+
+    /**
+     * Returns whether or not this event indicates an error condition.  This
+     * will never return {@code true} when {@code isConnected()} returns
+     * {@code true}.
+     *
+     * @return {@code true} if the event indicates a terminal error has
+     *  occurred, {@code false} otherwise.
+     */
+    public boolean isError() {
+        return cause != null;
+    }
+
+    /**
+     * Returns the underlying cause of the error condition.  This method is
+     * guaranteed to return {@code null} when @{code isError()} returns
+     * {@code false}.  Similarly, this method is guaranteed to return
+     * non-@{code null} if {@code isError()} returns {@code true}.
+     *
+     * @return underlying cause of the error condition, or {@code null} if
+     *  this event does not represent an error condition
+     */
+    public Throwable getCause() {
+        return cause;
+    }
+
+    /**
+     * Get the list of requests which may not have been sent or were not
+     * acknowledged by the remote connection manager prior to session
+     * termination.
+     *
+     * @return list of messages which may not have been received by the remote
+     *  connection manager, or an empty list if the session is still connected
+     */
+    public List<ComposableBody> getOutstandingRequests() {
+        return requests;
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/BOSHClientConnListener.java b/src/com/kenai/jbosh/BOSHClientConnListener.java
new file mode 100644
index 0000000..6d646cb
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClientConnListener.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Interface used by parties interested in monitoring the connection state
+ * of a client session.
+ */
+public interface BOSHClientConnListener {
+
+    /**
+     * Called when the connection state of the client which the listener
+     * is registered against has changed.  The event object supplied can
+     * be used to determine the current session state.
+     *
+     * @param connEvent connection event describing the state
+     */
+    void connectionEvent(BOSHClientConnEvent connEvent);
+    
+}
diff --git a/src/com/kenai/jbosh/BOSHClientRequestListener.java b/src/com/kenai/jbosh/BOSHClientRequestListener.java
new file mode 100644
index 0000000..2cc92f3
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClientRequestListener.java
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Interface used by parties interested in monitoring outbound requests made
+ * by the client to the connection manager (CM).  No opportunity is provided
+ * to manipulate the outbound request.
+ * <p/>
+ * The messages being sent are typically modified copies of the message
+ * body provided to the {@code BOSHClient} instance, built from the
+ * originally provided message body plus additional BOSH protocol
+ * state and information.  Messages may also be sent automatically when the
+ * protocol requires it, such as maintaining a minimum number of open
+ * connections to the connection manager.
+ * <p/>
+ * Listeners are executed by the sending thread immediately prior to
+ * message transmission and should not block for any significant amount
+ * of time.
+ */
+public interface BOSHClientRequestListener {
+
+    /**
+     * Called when the listener is being notified that a client request is
+     * about to be sent to the connection manager.
+     *
+     * @param event event instance containing the message being sent
+     */
+    void requestSent(BOSHMessageEvent event);
+
+}
diff --git a/src/com/kenai/jbosh/BOSHClientResponseListener.java b/src/com/kenai/jbosh/BOSHClientResponseListener.java
new file mode 100644
index 0000000..1d86e4f
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHClientResponseListener.java
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Interface used by parties interested in monitoring inbound responses
+ * to the client from the connection manager (CM).  No opportunity is provided
+ * to manipulate the response.
+ * <p/>
+ * Listeners are executed by the message processing thread and should not
+ * block for any significant amount of time.
+ */
+public interface BOSHClientResponseListener {
+
+    /**
+     * Called when the listener is being notified that a response has been
+     * received from the connection manager.
+     *
+     * @param event event instance containing the message being sent
+     */
+    void responseReceived(BOSHMessageEvent event);
+
+}
diff --git a/src/com/kenai/jbosh/BOSHException.java b/src/com/kenai/jbosh/BOSHException.java
new file mode 100644
index 0000000..e0bc05b
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHException.java
@@ -0,0 +1,50 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Exception class used by the BOSH API to minimize the number of checked
+ * exceptions which must be handled by the user of the API.
+ */
+public class BOSHException extends Exception {
+
+    /**
+     * Servial version UID.
+     */
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Creates a new exception isntance with the specified descriptive message.
+     *
+     * @param msg description of the exceptional condition
+     */
+    public BOSHException(final String msg) {
+        super(msg);
+    }
+
+    /**
+     * Creates a new exception isntance with the specified descriptive
+     * message and the underlying root cause of the exceptional condition.
+     *
+     * @param msg description of the exceptional condition
+     * @param cause root cause or instigator of the condition
+     */
+    public BOSHException(final String msg, final Throwable cause) {
+        super(msg, cause);
+    }
+
+}
diff --git a/src/com/kenai/jbosh/BOSHMessageEvent.java b/src/com/kenai/jbosh/BOSHMessageEvent.java
new file mode 100644
index 0000000..550903e
--- /dev/null
+++ b/src/com/kenai/jbosh/BOSHMessageEvent.java
@@ -0,0 +1,92 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.EventObject;
+
+/**
+ * Event representing a message sent to or from a BOSH connection manager.
+ * <p/>
+ * This class is immutable and thread-safe.
+ */
+public final class BOSHMessageEvent extends EventObject {
+
+    /**
+     * Serialized version.
+     */
+    private static final long serialVersionUID = 1L;
+    
+    /**
+     * Message which was sent or received.
+     */
+    private final AbstractBody body;
+
+    /**
+     * Creates a new message event instance.
+     *
+     * @param source event source
+     * @param cBody message body
+     */
+    private BOSHMessageEvent(
+            final Object source,
+            final AbstractBody cBody) {
+        super(source);
+        if (cBody == null) {
+            throw(new IllegalArgumentException(
+                    "message body may not be null"));
+        }
+        body = cBody;
+    }
+
+    /**
+     * Creates a new message event for clients sending events to the
+     * connection manager.
+     *
+     * @param source sender of the message
+     * @param body message body
+     * @return event instance
+     */
+    static BOSHMessageEvent createRequestSentEvent(
+            final BOSHClient source,
+            final AbstractBody body) {
+        return new BOSHMessageEvent(source, body);
+    }
+
+    /**
+     * Creates a new message event for clients receiving new messages
+     * from the connection manager.
+     *
+     * @param source receiver of the message
+     * @param body message body
+     * @return event instance
+     */
+    static BOSHMessageEvent createResponseReceivedEvent(
+            final BOSHClient source,
+            final AbstractBody body) {
+        return new BOSHMessageEvent(source, body);
+    }
+
+    /**
+     * Gets the message body which was sent or received.
+     *
+     * @return message body
+     */
+    public AbstractBody getBody() {
+        return body;
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/BodyParser.java b/src/com/kenai/jbosh/BodyParser.java
new file mode 100644
index 0000000..5ef5276
--- /dev/null
+++ b/src/com/kenai/jbosh/BodyParser.java
@@ -0,0 +1,36 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Interface for parser implementations to implement in order to abstract the
+ * business of XML parsing out of the Body class.  This allows us to leverage
+ * a variety of parser implementations to gain performance advantages.
+ */
+interface BodyParser {
+
+    /**
+     * Parses the XML message, extracting the useful data from the initial
+     * body element and returning it in a results object.
+     *
+     * @param xml XML to parse
+     * @return useful data parsed out of the XML
+     * @throws BOSHException on parse error
+     */
+    BodyParserResults parse(String xml) throws BOSHException;
+
+}
diff --git a/src/com/kenai/jbosh/BodyParserResults.java b/src/com/kenai/jbosh/BodyParserResults.java
new file mode 100644
index 0000000..955e4bf
--- /dev/null
+++ b/src/com/kenai/jbosh/BodyParserResults.java
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Data extracted from a raw XML message by a BodyParser implementation.
+ * Currently, this is limited to the attributes of the wrapper element.
+ */
+final class BodyParserResults {
+
+    /**
+     * Map of qualified names to their values.  This map is defined to
+     * match the requirement of the {@code Body} class to prevent
+     * excessive copying.
+     */
+    private final Map<BodyQName, String> attrs =
+            new HashMap<BodyQName, String>();
+
+    /**
+     * Constructor.
+     */
+    BodyParserResults() {
+        // Empty
+    }
+
+    /**
+     * Add an attribute definition to the results.
+     *
+     * @param name attribute's qualified name
+     * @param value attribute value
+     */
+    void addBodyAttributeValue(
+            final BodyQName name,
+            final String value) {
+        attrs.put(name, value);
+    }
+
+    /**
+     * Returns the map of attributes added by the parser.
+     *
+     * @return map of atributes. Note: This is the live instance, not a copy.
+     */
+    Map<BodyQName, String> getAttributes() {
+        return attrs;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/BodyParserSAX.java b/src/com/kenai/jbosh/BodyParserSAX.java
new file mode 100644
index 0000000..54c6c01
--- /dev/null
+++ b/src/com/kenai/jbosh/BodyParserSAX.java
@@ -0,0 +1,206 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.lang.ref.SoftReference;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import javax.xml.parsers.ParserConfigurationException;
+import javax.xml.parsers.SAXParser;
+import javax.xml.parsers.SAXParserFactory;
+import org.xml.sax.Attributes;
+import org.xml.sax.SAXException;
+import org.xml.sax.helpers.DefaultHandler;
+
+/**
+ * Implementation of the BodyParser interface which uses the SAX API
+ * that is part of the JDK.  Due to the fact that we can cache and reuse
+ * SAXPArser instances, this has proven to be significantly faster than the
+ * use of the javax.xml.stream API introduced in Java 6 while simultaneously
+ * providing an implementation accessible to Java 5 users.
+ */
+final class BodyParserSAX implements BodyParser {
+
+    /**
+     * Logger.
+     */
+    private static final Logger LOG =
+            Logger.getLogger(BodyParserSAX.class.getName());
+
+    /**
+     * SAX parser factory.
+     */
+    private static final SAXParserFactory SAX_FACTORY;
+    static {
+        SAX_FACTORY = SAXParserFactory.newInstance();
+        SAX_FACTORY.setNamespaceAware(true);
+        SAX_FACTORY.setValidating(false);
+    }
+
+    /**
+     * Thread local to contain a SAX parser instance for each thread that
+     * attempts to use one.  This allows us to gain an order of magnitude of
+     * performance as a result of not constructing parsers for each
+     * invocation while retaining thread safety.
+     */
+    private static final ThreadLocal<SoftReference<SAXParser>> PARSER =
+        new ThreadLocal<SoftReference<SAXParser>>() {
+            @Override protected SoftReference<SAXParser> initialValue() {
+                return new SoftReference<SAXParser>(null);
+            }
+        };
+
+    /**
+     * SAX event handler class.
+     */
+    private static final class Handler extends DefaultHandler {
+        private final BodyParserResults result;
+        private final SAXParser parser;
+        private String defaultNS = null;
+
+        private Handler(SAXParser theParser, BodyParserResults results) {
+            parser = theParser;
+            result = results;
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public void startElement(
+                final String uri,
+                final String localName,
+                final String qName,
+                final Attributes attributes) {
+            if (LOG.isLoggable(Level.FINEST)) {
+                LOG.finest("Start element: " + qName);
+                LOG.finest("    URI: " + uri);
+                LOG.finest("    local: " + localName);
+            }
+
+            BodyQName bodyName = AbstractBody.getBodyQName();
+            // Make sure the first element is correct
+            if (!(bodyName.getNamespaceURI().equals(uri)
+                    && bodyName.getLocalPart().equals(localName))) {
+                throw(new IllegalStateException(
+                        "Root element was not '" + bodyName.getLocalPart()
+                        + "' in the '" + bodyName.getNamespaceURI()
+                        + "' namespace.  (Was '" + localName + "' in '" + uri
+                        + "')"));
+            }
+
+            // Read in the attributes, making sure to expand the namespaces
+            // as needed.
+            for (int idx=0; idx < attributes.getLength(); idx++) {
+                String attrURI = attributes.getURI(idx);
+                if (attrURI.length() == 0) {
+                    attrURI = defaultNS;
+                }
+                String attrLN = attributes.getLocalName(idx);
+                String attrVal = attributes.getValue(idx);
+                if (LOG.isLoggable(Level.FINEST)) {
+                    LOG.finest("    Attribute: {" + attrURI + "}"
+                            + attrLN + " = '" + attrVal + "'");
+                }
+
+                BodyQName aqn = BodyQName.create(attrURI, attrLN);
+                result.addBodyAttributeValue(aqn, attrVal);
+            }
+            
+            parser.reset();
+        }
+
+        /**
+         * {@inheritDoc}
+         *
+         * This implementation uses this event hook to keep track of the
+         * default namespace on the body element.
+         */
+        @Override
+        public void startPrefixMapping(
+                final String prefix,
+                final String uri) {
+            if (prefix.length() == 0) {
+                if (LOG.isLoggable(Level.FINEST)) {
+                    LOG.finest("Prefix mapping: <DEFAULT> => " + uri);
+                }
+                defaultNS = uri;
+            } else {
+                if (LOG.isLoggable(Level.FINEST)) {
+                    LOG.info("Prefix mapping: " + prefix + " => " + uri);
+                }
+            }
+        }
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // BodyParser interface methods:
+
+    /**
+     * {@inheritDoc}
+     */
+    public BodyParserResults parse(String xml) throws BOSHException {
+        BodyParserResults result = new BodyParserResults();
+        Exception thrown;
+        try {
+            InputStream inStream = new ByteArrayInputStream(xml.getBytes());
+            SAXParser parser = getSAXParser();
+            parser.parse(inStream, new Handler(parser, result));
+            return result;
+        } catch (SAXException saxx) {
+            thrown = saxx;
+        } catch (IOException iox) {
+            thrown = iox;
+        }
+        throw(new BOSHException("Could not parse body:\n" + xml, thrown));
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Gets a SAXParser for use in parsing incoming messages.
+     *
+     * @return parser instance
+     */
+    private static SAXParser getSAXParser() {
+        SoftReference<SAXParser> ref = PARSER.get();
+        SAXParser result = ref.get();
+        if (result == null) {
+            Exception thrown;
+            try {
+                result = SAX_FACTORY.newSAXParser();
+                ref = new SoftReference<SAXParser>(result);
+                PARSER.set(ref);
+                return result;
+            } catch (ParserConfigurationException ex) {
+                thrown = ex;
+            } catch (SAXException ex) {
+                thrown = ex;
+            }
+            throw(new IllegalStateException(
+                    "Could not create SAX parser", thrown));
+        } else {
+            result.reset();
+            return result;
+        }
+    }
+    
+}
diff --git a/src/com/kenai/jbosh/BodyParserXmlPull.java b/src/com/kenai/jbosh/BodyParserXmlPull.java
new file mode 100644
index 0000000..5f23b06
--- /dev/null
+++ b/src/com/kenai/jbosh/BodyParserXmlPull.java
@@ -0,0 +1,165 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.IOException;
+import java.io.StringReader;
+import java.lang.ref.SoftReference;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import javax.xml.XMLConstants;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+import org.xmlpull.v1.XmlPullParserFactory;
+
+/**
+ * Implementation of the BodyParser interface which uses the XmlPullParser
+ * API.  When available, this API provides an order of magnitude performance
+ * improvement over the default SAX parser implementation.
+ */
+final class BodyParserXmlPull implements BodyParser {
+
+    /**
+     * Logger.
+     */
+    private static final Logger LOG =
+            Logger.getLogger(BodyParserXmlPull.class.getName());
+
+    /**
+     * Thread local to contain a XmlPullParser instance for each thread that
+     * attempts to use one.  This allows us to gain an order of magnitude of
+     * performance as a result of not constructing parsers for each
+     * invocation while retaining thread safety.
+     */
+    private static final ThreadLocal<SoftReference<XmlPullParser>> XPP_PARSER =
+        new ThreadLocal<SoftReference<XmlPullParser>>() {
+            @Override protected SoftReference<XmlPullParser> initialValue() {
+                return new SoftReference<XmlPullParser>(null);
+            }
+        };
+
+    ///////////////////////////////////////////////////////////////////////////
+    // BodyParser interface methods:
+
+    /**
+     * {@inheritDoc}
+     */
+    public BodyParserResults parse(final String xml) throws BOSHException {
+        BodyParserResults result = new BodyParserResults();
+        Exception thrown;
+        try {
+            XmlPullParser xpp = getXmlPullParser();
+
+            xpp.setInput(new StringReader(xml));
+            int eventType = xpp.getEventType();
+            while (eventType != XmlPullParser.END_DOCUMENT) {
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (LOG.isLoggable(Level.FINEST)) {
+                        LOG.finest("Start tag: " + xpp.getName());
+                    }
+                } else {
+                    eventType = xpp.next();
+                    continue;
+                }
+
+                String prefix = xpp.getPrefix();
+                if (prefix == null) {
+                    prefix = XMLConstants.DEFAULT_NS_PREFIX;
+                }
+                String uri = xpp.getNamespace();
+                String localName = xpp.getName();
+                QName name = new QName(uri, localName, prefix);
+                if (LOG.isLoggable(Level.FINEST)) {
+                    LOG.finest("Start element: ");
+                    LOG.finest("    prefix: " + prefix);
+                    LOG.finest("    URI: " + uri);
+                    LOG.finest("    local: " + localName);
+                }
+
+                BodyQName bodyName = AbstractBody.getBodyQName();
+                if (!bodyName.equalsQName(name)) {
+                    throw(new IllegalStateException(
+                            "Root element was not '" + bodyName.getLocalPart()
+                            + "' in the '" + bodyName.getNamespaceURI()
+                            + "' namespace.  (Was '" + localName
+                            + "' in '" + uri + "')"));
+                }
+
+                for (int idx=0; idx < xpp.getAttributeCount(); idx++) {
+                    String attrURI = xpp.getAttributeNamespace(idx);
+                    if (attrURI.length() == 0) {
+                        attrURI = xpp.getNamespace(null);
+                    }
+                    String attrPrefix = xpp.getAttributePrefix(idx);
+                    if (attrPrefix == null) {
+                        attrPrefix = XMLConstants.DEFAULT_NS_PREFIX;
+                    }
+                    String attrLN = xpp.getAttributeName(idx);
+                    String attrVal = xpp.getAttributeValue(idx);
+                    BodyQName aqn = BodyQName.createWithPrefix(
+                            attrURI, attrLN, attrPrefix);
+                    if (LOG.isLoggable(Level.FINEST)) {
+                        LOG.finest("        Attribute: {" + attrURI + "}"
+                                + attrLN + " = '" + attrVal + "'");
+                    }
+                    result.addBodyAttributeValue(aqn, attrVal);
+                }
+                break;
+            }
+            return result;
+        } catch (RuntimeException rtx) {
+            thrown = rtx;
+        } catch (XmlPullParserException xmlppx) {
+            thrown = xmlppx;
+        } catch (IOException iox) {
+            thrown = iox;
+        }
+        throw(new BOSHException("Could not parse body:\n" + xml, thrown));
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Gets a XmlPullParser for use in parsing incoming messages.
+     *
+     * @return parser instance
+     */
+    private static XmlPullParser getXmlPullParser() {
+        SoftReference<XmlPullParser> ref = XPP_PARSER.get();
+        XmlPullParser result = ref.get();
+        if (result == null) {
+            Exception thrown;
+            try {
+                XmlPullParserFactory factory = XmlPullParserFactory.newInstance();
+                factory.setNamespaceAware(true);
+                factory.setValidating(false);
+                result = factory.newPullParser();
+                ref = new SoftReference<XmlPullParser>(result);
+                XPP_PARSER.set(ref);
+                return result;
+            } catch (Exception ex) {
+                thrown = ex;
+            }
+            throw(new IllegalStateException(
+                    "Could not create XmlPull parser", thrown));
+        } else {
+            return result;
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/BodyQName.java b/src/com/kenai/jbosh/BodyQName.java
new file mode 100644
index 0000000..83acdf1
--- /dev/null
+++ b/src/com/kenai/jbosh/BodyQName.java
@@ -0,0 +1,165 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Qualified name of an attribute of the wrapper element.  This class is
+ * analagous to the {@code javax.xml.namespace.QName} class.
+ * Each qualified name consists of a namespace URI and a local name.
+ * <p/>
+ * Instances of this class are immutable and thread-safe.
+ */
+public final class BodyQName {
+
+    /**
+     * BOSH namespace URI.
+     */
+    static final String BOSH_NS_URI =
+            "http://jabber.org/protocol/httpbind";
+
+    /**
+     * Namespace URI.
+     */
+    private final QName qname;
+
+    /**
+     * Private constructor to prevent direct construction.
+     *
+     * @param wrapped QName instance to wrap
+     */
+    private BodyQName(
+            final QName wrapped) {
+        qname = wrapped;
+    }
+
+    /**
+     * Creates a new qualified name using a namespace URI and local name.
+     *
+     * @param uri namespace URI
+     * @param local local name
+     * @return BodyQName instance
+     */
+    public static BodyQName create(
+            final String uri,
+            final String local) {
+        return createWithPrefix(uri, local, null);
+    }
+
+    /**
+     * Creates a new qualified name using a namespace URI and local name
+     * along with an optional prefix.
+     *
+     * @param uri namespace URI
+     * @param local local name
+     * @param prefix optional prefix or @{code null} for no prefix
+     * @return BodyQName instance
+     */
+    public static BodyQName createWithPrefix(
+            final String uri,
+            final String local,
+            final String prefix) {
+        if (uri == null || uri.length() == 0) {
+            throw(new IllegalArgumentException(
+                    "URI is required and may not be null/empty"));
+        }
+        if (local == null || local.length() == 0) {
+            throw(new IllegalArgumentException(
+                    "Local arg is required and may not be null/empty"));
+        }
+        if (prefix == null || prefix.length() == 0) {
+            return new BodyQName(new QName(uri, local));
+        } else {
+            return new BodyQName(new QName(uri, local, prefix));
+        }
+    }
+
+    /**
+     * Get the namespace URI of this qualified name.
+     *
+     * @return namespace uri
+     */
+    public String getNamespaceURI() {
+        return qname.getNamespaceURI();
+    }
+
+    /**
+     * Get the local part of this qualified name.
+     *
+     * @return local name
+     */
+    public String  getLocalPart() {
+        return qname.getLocalPart();
+    }
+
+    /**
+     * Get the optional prefix used with this qualified name, or {@code null}
+     * if no prefix has been assiciated.
+     *
+     * @return prefix, or {@code null} if no prefix was supplied
+     */
+    public String getPrefix() {
+        return qname.getPrefix();
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public boolean equals(final Object obj) {
+        if (obj instanceof BodyQName) {
+            BodyQName other = (BodyQName) obj;
+            return qname.equals(other.qname);
+        } else {
+            return false;
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public int hashCode() {
+        return qname.hashCode();
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Creates a new qualified name using the BOSH namespace URI and local name.
+     *
+     * @param local local name
+     * @return BodyQName instance
+     */
+    static BodyQName createBOSH(
+            final String local) {
+        return createWithPrefix(BOSH_NS_URI, local, null);
+    }
+
+    /**
+     * Convenience method to compare this qualified name with a
+     * {@code javax.xml.namespace.QName}.
+     *
+     * @param otherName QName to compare to
+     * @return @{code true} if the qualified name is the same, {@code false}
+     *  otherwise
+     */
+    boolean equalsQName(final QName otherName) {
+        return qname.equals(otherName);
+    }
+
+}
diff --git a/src/com/kenai/jbosh/CMSessionParams.java b/src/com/kenai/jbosh/CMSessionParams.java
new file mode 100644
index 0000000..bbed628
--- /dev/null
+++ b/src/com/kenai/jbosh/CMSessionParams.java
@@ -0,0 +1,177 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * A BOSH connection manager session instance.  This consolidates the
+ * configuration knowledge related to the CM session and provides a
+ * mechanism by which
+ */
+final class CMSessionParams {
+
+    private final AttrSessionID sid;
+
+    private final AttrWait wait;
+
+    private final AttrVersion ver;
+
+    private final AttrPolling polling;
+
+    private final AttrInactivity inactivity;
+
+    private final AttrRequests requests;
+
+    private final AttrHold hold;
+
+    private final AttrAccept accept;
+
+    private final AttrMaxPause maxPause;
+
+    private final AttrAck ack;
+
+    private final AttrCharsets charsets;
+
+    private final boolean ackingRequests;
+
+    /**
+     * Prevent direct construction.
+     */
+    private CMSessionParams(
+            final AttrSessionID aSid,
+            final AttrWait aWait,
+            final AttrVersion aVer,
+            final AttrPolling aPolling,
+            final AttrInactivity aInactivity,
+            final AttrRequests aRequests,
+            final AttrHold aHold,
+            final AttrAccept aAccept,
+            final AttrMaxPause aMaxPause,
+            final AttrAck aAck,
+            final AttrCharsets aCharsets,
+            final boolean amAckingRequests) {
+        sid = aSid;
+        wait = aWait;
+        ver = aVer;
+        polling = aPolling;
+        inactivity = aInactivity;
+        requests = aRequests;
+        hold = aHold;
+        accept = aAccept;
+        maxPause = aMaxPause;
+        ack = aAck;
+        charsets = aCharsets;
+        ackingRequests = amAckingRequests;
+    }
+
+    static CMSessionParams fromSessionInit(
+            final AbstractBody req,
+            final AbstractBody resp)
+    throws BOSHException {
+        AttrAck aAck = AttrAck.createFromString(
+                resp.getAttribute(Attributes.ACK));
+        String rid = req.getAttribute(Attributes.RID);
+        boolean acking = (aAck != null && aAck.getValue().equals(rid));
+
+        return new CMSessionParams(
+            AttrSessionID.createFromString(
+                getRequiredAttribute(resp, Attributes.SID)),
+            AttrWait.createFromString(
+                getRequiredAttribute(resp, Attributes.WAIT)),
+            AttrVersion.createFromString(
+                resp.getAttribute(Attributes.VER)),
+            AttrPolling.createFromString(
+                resp.getAttribute(Attributes.POLLING)),
+            AttrInactivity.createFromString(
+                resp.getAttribute(Attributes.INACTIVITY)),
+            AttrRequests.createFromString(
+                resp.getAttribute(Attributes.REQUESTS)),
+            AttrHold.createFromString(
+                resp.getAttribute(Attributes.HOLD)),
+            AttrAccept.createFromString(
+                resp.getAttribute(Attributes.ACCEPT)),
+            AttrMaxPause.createFromString(
+                resp.getAttribute(Attributes.MAXPAUSE)),
+            aAck,
+            AttrCharsets.createFromString(
+                resp.getAttribute(Attributes.CHARSETS)),
+            acking
+            );
+    }
+
+    private static String getRequiredAttribute(
+            final AbstractBody body,
+            final BodyQName name)
+    throws BOSHException {
+        String attrStr = body.getAttribute(name);
+        if (attrStr == null) {
+            throw(new BOSHException(
+                    "Connection Manager session creation response did not "
+                    + "include required '" + name.getLocalPart()
+                    + "' attribute"));
+        }
+        return attrStr;
+    }
+
+    AttrSessionID getSessionID() {
+        return sid;
+    }
+
+    AttrWait getWait() {
+        return wait;
+    }
+
+    AttrVersion getVersion() {
+        return ver;
+    }
+
+    AttrPolling getPollingInterval() {
+        return polling;
+    }
+
+    AttrInactivity getInactivityPeriod() {
+        return inactivity;
+    }
+
+    AttrRequests getRequests() {
+        return requests;
+    }
+
+    AttrHold getHold() {
+        return hold;
+    }
+
+    AttrAccept getAccept() {
+        return accept;
+    }
+
+    AttrMaxPause getMaxPause() {
+        return maxPause;
+    }
+
+    AttrAck getAck() {
+        return ack;
+    }
+    
+    AttrCharsets getCharsets() {
+        return charsets;
+    }
+
+    boolean isAckingRequests() {
+        return ackingRequests;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/ComposableBody.java b/src/com/kenai/jbosh/ComposableBody.java
new file mode 100644
index 0000000..d375478
--- /dev/null
+++ b/src/com/kenai/jbosh/ComposableBody.java
@@ -0,0 +1,345 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicReference;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+import javax.xml.XMLConstants;
+
+/**
+ * Implementation of the {@code AbstractBody} class which allows for the
+ * definition of  messages from individual elements of a body.
+ * <p/>
+ * A message is constructed by creating a builder, manipulating the
+ * configuration of the builder, and then building it into a class instance,
+ * as in the following example:
+ * <pre>
+ * ComposableBody body = ComposableBody.builder()
+ *     .setNamespaceDefinition("foo", "http://foo.com/bar")
+ *     .setPayloadXML("<foo:data>Data to send to remote server</foo:data>")
+ *     .build();
+ * </pre>
+ * Class instances can also be "rebuilt", allowing them to be used as templates
+ * when building many similar messages:
+ * <pre>
+ * ComposableBody body2 = body.rebuild()
+ *     .setPayloadXML("<foo:data>More data to send</foo:data>")
+ *     .build();
+ * </pre>
+ * This class does only minimal syntactic and semantic checking with respect
+ * to what the generated XML will look like.  It is up to the developer to
+ * protect against the definition of malformed XML messages when building
+ * instances of this class.
+ * <p/>
+ * Instances of this class are immutable and thread-safe.
+ */
+public final class ComposableBody extends AbstractBody {
+
+    /**
+     * Pattern used to identify the beginning {@code body} element of a
+     * BOSH message.
+     */
+    private static final Pattern BOSH_START =
+            Pattern.compile("<" + "(?:(?:[^:\t\n\r >]+:)|(?:\\{[^\\}>]*?}))?"
+            + "body" + "(?:[\t\n\r ][^>]*?)?" + "(/>|>)");
+
+    /**
+     * Map of all attributes to their values.
+     */
+    private final Map<BodyQName, String> attrs;
+
+    /**
+     * Payload XML.
+     */
+    private final String payload;
+
+    /**
+     * Computed raw XML.
+     */
+    private final AtomicReference<String> computed =
+            new AtomicReference<String>();
+
+    /**
+     * Class instance builder, after the builder pattern.  This allows each
+     * message instance to be immutable while providing flexibility when
+     * building new messages.
+     * <p/>
+     * Instances of this class are <b>not</b> thread-safe.
+     */
+    public static final class Builder {
+        private Map<BodyQName, String> map;
+        private boolean doMapCopy;
+        private String payloadXML;
+
+        /**
+         * Prevent direct construction.
+         */
+        private Builder() {
+            // Empty
+        }
+
+        /**
+         * Creates a builder which is initialized to the values of the
+         * provided {@code ComposableBody} instance.  This allows an
+         * existing {@code ComposableBody} to be used as a
+         * template/starting point.
+         *
+         * @param source body template
+         * @return builder instance
+         */
+        private static Builder fromBody(final ComposableBody source) {
+            Builder result = new Builder();
+            result.map = source.getAttributes();
+            result.doMapCopy = true;
+            result.payloadXML = source.payload;
+            return result;
+        }
+
+        /**
+         * Set the body message's wrapped payload content.  Any previous
+         * content will be replaced.
+         *
+         * @param xml payload XML content
+         * @return builder instance
+         */
+        public Builder setPayloadXML(final String xml) {
+            if (xml == null) {
+                throw(new IllegalArgumentException(
+                        "payload XML argument cannot be null"));
+            }
+            payloadXML = xml;
+            return this;
+        }
+
+        /**
+         * Set an attribute on the message body / wrapper element.
+         *
+         * @param name qualified name of the attribute
+         * @param value value of the attribute
+         * @return builder instance
+         */
+        public Builder setAttribute(
+                final BodyQName name, final String value) {
+            if (map == null) {
+                map = new HashMap<BodyQName, String>();
+            } else if (doMapCopy) {
+                map = new HashMap<BodyQName, String>(map);
+                doMapCopy = false;
+            }
+            if (value == null) {
+                map.remove(name);
+            } else {
+                map.put(name, value);
+            }
+            return this;
+        }
+
+        /**
+         * Convenience method to set a namespace definition. This would result
+         * in a namespace prefix definition similar to:
+         * {@code <body xmlns:prefix="uri"/>}
+         *
+         * @param prefix prefix to define
+         * @param uri namespace URI to associate with the prefix
+         * @return builder instance
+         */
+        public Builder setNamespaceDefinition(
+                final String prefix, final String uri) {
+            BodyQName qname = BodyQName.createWithPrefix(
+                    XMLConstants.XML_NS_URI, prefix,
+                    XMLConstants.XMLNS_ATTRIBUTE);
+            return setAttribute(qname, uri);
+        }
+
+        /**
+         * Build the immutable object instance with the current configuration.
+         *
+         * @return composable body instance
+         */
+        public ComposableBody build() {
+            if (map == null) {
+                map = new HashMap<BodyQName, String>();
+            }
+            if (payloadXML == null) {
+                payloadXML = "";
+            }
+            return new ComposableBody(map, payloadXML);
+        }
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent direct construction.  This constructor is for body messages
+     * which are dynamically assembled.
+     */
+    private ComposableBody(
+            final Map<BodyQName, String> attrMap,
+            final String payloadXML) {
+        super();
+        attrs = attrMap;
+        payload = payloadXML;
+    }
+
+    /**
+     * Parse a static body instance into a composable instance.  This is an
+     * expensive operation and should not be used lightly.
+     * <p/>
+     * The current implementation does not obtain the payload XML by means of
+     * a proper XML parser.  It uses some string pattern searching to find the
+     * first @{code body} element and the last element's closing tag.  It is
+     * assumed that the static body's XML is well formed, etc..  This
+     * implementation may change in the future.
+     *
+     * @param body static body instance to convert
+     * @return composable bosy instance
+     * @throws BOSHException
+     */
+    static ComposableBody fromStaticBody(final StaticBody body)
+    throws BOSHException {
+        String raw = body.toXML();
+        Matcher matcher = BOSH_START.matcher(raw);
+        if (!matcher.find()) {
+            throw(new BOSHException(
+                    "Could not locate 'body' element in XML.  The raw XML did"
+                    + " not match the pattern: " + BOSH_START));
+        }
+        String payload;
+        if (">".equals(matcher.group(1))) {
+            int first = matcher.end();
+            int last = raw.lastIndexOf("</");
+            if (last < first) {
+                last = first;
+            }
+            payload = raw.substring(first, last);
+        } else {
+            payload = "";
+        }
+
+        return new ComposableBody(body.getAttributes(), payload);
+    }
+
+    /**
+     * Create a builder instance to build new instances of this class.
+     *
+     * @return AbstractBody instance
+     */
+    public static Builder builder() {
+        return new Builder();
+    }
+
+    /**
+     * If this {@code ComposableBody} instance is a dynamic instance, uses this
+     * {@code ComposableBody} instance as a starting point, create a builder
+     * which can be used to create another {@code ComposableBody} instance
+     * based on this one. This allows a {@code ComposableBody} instance to be
+     * used as a template.  Note that the use of the returned builder in no
+     * way modifies or manipulates the current {@code ComposableBody} instance.
+     *
+     * @return builder instance which can be used to build similar
+     *  {@code ComposableBody} instances
+     */
+    public Builder rebuild() {
+        return Builder.fromBody(this);
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Accessors:
+    
+    /**
+     * {@inheritDoc}
+     */
+    public Map<BodyQName, String> getAttributes() {
+        return Collections.unmodifiableMap(attrs);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public String toXML() {
+        String comp = computed.get();
+        if (comp == null) {
+            comp = computeXML();
+            computed.set(comp);
+        }
+        return comp;
+    }
+
+    /**
+     * Get the paylaod XML in String form.
+     *
+     * @return payload XML
+     */
+    public String getPayloadXML() {
+        return payload;
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Escape the value of an attribute to ensure we maintain valid
+     * XML syntax.
+     *
+     * @param value value to escape
+     * @return escaped value
+     */
+    private String escape(final String value) {
+        return value.replace("'", "&apos;");
+    }
+
+    /**
+     * Generate a String representation of the message body.
+     *
+     * @return XML string representation of the body
+     */
+    private String computeXML() {
+        BodyQName bodyName = getBodyQName();
+        StringBuilder builder = new StringBuilder();
+        builder.append("<");
+        builder.append(bodyName.getLocalPart());
+        for (Map.Entry<BodyQName, String> entry : attrs.entrySet()) {
+            builder.append(" ");
+            BodyQName name = entry.getKey();
+            String prefix = name.getPrefix();
+            if (prefix != null && prefix.length() > 0) {
+                builder.append(prefix);
+                builder.append(":");
+            }
+            builder.append(name.getLocalPart());
+            builder.append("='");
+            builder.append(escape(entry.getValue()));
+            builder.append("'");
+        }
+        builder.append(" ");
+        builder.append(XMLConstants.XMLNS_ATTRIBUTE);
+        builder.append("='");
+        builder.append(bodyName.getNamespaceURI());
+        builder.append("'>");
+        if (payload != null) {
+            builder.append(payload);
+        }
+        builder.append("</body>");
+        return builder.toString();
+    }
+
+}
diff --git a/src/com/kenai/jbosh/GZIPCodec.java b/src/com/kenai/jbosh/GZIPCodec.java
new file mode 100644
index 0000000..988f27f
--- /dev/null
+++ b/src/com/kenai/jbosh/GZIPCodec.java
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.zip.GZIPInputStream;
+import java.util.zip.GZIPOutputStream;
+
+/**
+ * Codec methods for compressing and uncompressing using GZIP.
+ */
+final class GZIPCodec {
+
+    /**
+     * Size of the internal buffer when decoding.
+     */
+    private static final int BUFFER_SIZE = 512;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent construction.
+     */
+    private GZIPCodec() {
+        // Empty
+    }
+
+    /**
+     * Returns the name of the codec.
+     *
+     * @return string name of the codec (i.e., "gzip")
+     */
+    public static String getID() {
+        return "gzip";
+    }
+
+    /**
+     * Compress/encode the data provided using the GZIP format.
+     *
+     * @param data data to compress
+     * @return compressed data
+     * @throws IOException on compression failure
+     */
+    public static byte[] encode(final byte[] data) throws IOException {
+        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
+        GZIPOutputStream gzOut = null;
+        try {
+            gzOut = new GZIPOutputStream(byteOut);
+            gzOut.write(data);
+            gzOut.close();
+            byteOut.close();
+            return byteOut.toByteArray();
+        } finally {
+            gzOut.close();
+            byteOut.close();
+        }
+    }
+
+    /**
+     * Uncompress/decode the data provided using the GZIP format.
+     *
+     * @param data data to uncompress
+     * @return uncompressed data
+     * @throws IOException on decompression failure
+     */
+    public static byte[] decode(final byte[] compressed) throws IOException {
+        ByteArrayInputStream byteIn = new ByteArrayInputStream(compressed);
+        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
+        GZIPInputStream gzIn = null;
+        try {
+            gzIn = new GZIPInputStream(byteIn);
+            int read;
+            byte[] buffer = new byte[BUFFER_SIZE];
+            do {
+                read = gzIn.read(buffer);
+                if (read > 0) {
+                    byteOut.write(buffer, 0, read);
+                }
+            } while (read >= 0);
+            return byteOut.toByteArray();
+        } finally {
+            gzIn.close();
+            byteOut.close();
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/HTTPExchange.java b/src/com/kenai/jbosh/HTTPExchange.java
new file mode 100644
index 0000000..c77caf0
--- /dev/null
+++ b/src/com/kenai/jbosh/HTTPExchange.java
@@ -0,0 +1,126 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.concurrent.locks.Condition;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+/**
+ * A request and response pair representing a single exchange with a remote
+ * content manager.  This is primarily a container class intended to maintain
+ * the relationship between the request and response but allows the response
+ * to be added after the fact.
+ */
+final class HTTPExchange {
+
+    /**
+     * Logger.
+     */
+    private static final Logger LOG =
+            Logger.getLogger(HTTPExchange.class.getName());
+    
+    /**
+     * Request body.
+     */
+    private final AbstractBody request;
+
+    /**
+     * Lock instance used to protect and provide conditions.
+     */
+    private final Lock lock = new ReentrantLock();
+
+    /**
+     * Condition used to signal when the response has been set.
+     */
+    private final Condition ready = lock.newCondition();
+
+    /**
+     * HTTPResponse instance.
+     */
+    private HTTPResponse response;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructor:
+
+    /**
+     * Create a new request/response pair object.
+     *
+     * @param req request message body
+     */
+    HTTPExchange(final AbstractBody req) {
+        if (req == null) {
+            throw(new IllegalArgumentException("Request body cannot be null"));
+        }
+        request = req;
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Get the original request message.
+     *
+     * @return request message body.
+     */
+    AbstractBody getRequest() {
+        return request;
+    }
+
+    /**
+     * Set the HTTPResponse instance.
+     *
+     * @return HTTPResponse instance associated with the request.
+     */
+    void setHTTPResponse(HTTPResponse resp) {
+        lock.lock();
+        try {
+            if (response != null) {
+                throw(new IllegalStateException(
+                        "HTTPResponse was already set"));
+            }
+            response = resp;
+            ready.signalAll();
+        } finally {
+            lock.unlock();
+        }
+    }
+
+    /**
+     * Get the HTTPResponse instance.
+     *
+     * @return HTTPResponse instance associated with the request.
+     */
+    HTTPResponse getHTTPResponse() {
+        lock.lock();
+        try {
+            while (response == null) {
+                try {
+                    ready.await();
+                } catch (InterruptedException intx) {
+                    LOG.log(Level.FINEST, "Interrupted", intx);
+                }
+            }
+            return response;
+        } finally {
+            lock.unlock();
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/HTTPResponse.java b/src/com/kenai/jbosh/HTTPResponse.java
new file mode 100644
index 0000000..f1f301c
--- /dev/null
+++ b/src/com/kenai/jbosh/HTTPResponse.java
@@ -0,0 +1,54 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * This class represents a complete HTTP response to a request made via
+ * a {@code HTTPSender} send request.  Instances of this interface are
+ * intended to represent a deferred, future response, not necessarily a
+ * response which is immediately available.
+ */
+interface HTTPResponse {
+
+    /**
+     * Close out any resources still held by the original request.  The
+     * conversation may need to be aborted if the session it was a part of
+     * gets abruptly terminated.
+     */
+    void abort();
+
+    /**
+     * Get the HTTP status code of the response (e.g., 200, 404, etc.).  If
+     * the response has not yet been received from the remote server, this
+     * method should block until the response has arrived.
+     *
+     * @return HTTP status code
+     * @throws InterruptedException if interrupted while awaiting response
+     */
+    int getHTTPStatus() throws InterruptedException, BOSHException;
+
+    /**
+     * Get the HTTP response message body.  If the response has not yet been
+     * received from the remote server, this method should block until the
+     * response has arrived.
+     *
+     * @return response message body
+     * @throws InterruptedException if interrupted while awaiting response
+     */
+    AbstractBody getBody() throws InterruptedException, BOSHException;
+    
+}
diff --git a/src/com/kenai/jbosh/HTTPSender.java b/src/com/kenai/jbosh/HTTPSender.java
new file mode 100644
index 0000000..486d274
--- /dev/null
+++ b/src/com/kenai/jbosh/HTTPSender.java
@@ -0,0 +1,54 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+/**
+ * Interface used to represent code which can send a BOSH XML body over
+ * HTTP to a connection manager.
+ */
+interface HTTPSender {
+
+    /**
+     * Initialize the HTTP sender instance for use with the session provided.
+     * This method will be called once before use of the service instance.
+     *
+     * @param sessionCfg session configuration
+     */
+    void init(BOSHClientConfig sessionCfg);
+
+    /**
+     * Dispose of all resources used to provide the required services.  This
+     * method will be called once when the service instance is no longer
+     * required.
+     */
+    void destroy();
+
+    /**
+     * Create a {@code Callable} instance which can be used to send the
+     * request specified to the connection manager.  This method should
+     * return immediately, prior to doing any real work.  The invocation
+     * of the returned {@code Callable} should send the request (if it has
+     * not already been sent by the time of the call), block while waiting
+     * for the response, and then return the response body.
+     *
+     * @param params CM session creation resopnse params
+     * @param body request body to send
+     * @return callable used to access the response
+     */
+    HTTPResponse send(CMSessionParams params, AbstractBody body);
+    
+}
diff --git a/src/com/kenai/jbosh/QName.java b/src/com/kenai/jbosh/QName.java
new file mode 100644
index 0000000..d395a06
--- /dev/null
+++ b/src/com/kenai/jbosh/QName.java
@@ -0,0 +1,269 @@
+/*
+ * The Apache Software License, Version 1.1
+ *
+ *
+ * Copyright (c) 2001-2003 The Apache Software Foundation.  All rights
+ * reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. The end-user documentation included with the redistribution,
+ *    if any, must include the following acknowledgment:
+ *       "This product includes software developed by the
+ *        Apache Software Foundation (http://www.apache.org/)."
+ *    Alternately, this acknowledgment may appear in the software itself,
+ *    if and wherever such third-party acknowledgments normally appear.
+ *
+ * 4. The names "Axis" and "Apache Software Foundation" must
+ *    not be used to endorse or promote products derived from this
+ *    software without prior written permission. For written
+ *    permission, please contact apache@apache.org.
+ *
+ * 5. Products derived from this software may not be called "Apache",
+ *    nor may "Apache" appear in their name, without prior written
+ *    permission of the Apache Software Foundation.
+ *
+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
+ * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This software consists of voluntary contributions made by many
+ * individuals on behalf of the Apache Software Foundation.  For more
+ * information on the Apache Software Foundation, please see
+ * <http://www.apache.org/>.
+ */
+package com.kenai.jbosh;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.Serializable;
+
+/**
+ * <code>QName</code> class represents the value of a qualified name
+ * as specified in <a href="http://www.w3.org/TR/xmlschema-2/#QName">XML
+ * Schema Part2: Datatypes specification</a>.
+ * <p>
+ * The value of a QName contains a <b>namespaceURI</b>, a <b>localPart</b> and a <b>prefix</b>.
+ * The localPart provides the local part of the qualified name. The
+ * namespaceURI is a URI reference identifying the namespace.
+ *
+ * @version 1.1
+ */
+public class QName implements Serializable {
+
+    /** comment/shared empty string */
+    private static final String emptyString = "".intern();
+
+    /** Field namespaceURI */
+    private String namespaceURI;
+
+    /** Field localPart */
+    private String localPart;
+
+    /** Field prefix */
+    private String prefix;
+
+    /**
+     * Constructor for the QName.
+     *
+     * @param localPart Local part of the QName
+     */
+    public QName(String localPart) {
+        this(emptyString, localPart, emptyString);
+    }
+
+    /**
+     * Constructor for the QName.
+     *
+     * @param namespaceURI Namespace URI for the QName
+     * @param localPart Local part of the QName.
+     */
+    public QName(String namespaceURI, String localPart) {
+        this(namespaceURI, localPart, emptyString);
+    }
+
+    /**
+     * Constructor for the QName.
+     *
+     * @param namespaceURI Namespace URI for the QName
+     * @param localPart Local part of the QName.
+     * @param prefix Prefix of the QName.
+     */
+    public QName(String namespaceURI, String localPart, String prefix) {
+        this.namespaceURI = (namespaceURI == null)
+                ? emptyString
+                : namespaceURI.intern();
+        if (localPart == null) {
+            throw new IllegalArgumentException("invalid QName local part");
+        } else {
+            this.localPart = localPart.intern();
+        }
+
+        if (prefix == null) {
+            throw new IllegalArgumentException("invalid QName prefix");
+        } else {
+            this.prefix = prefix.intern();
+        }
+    }
+
+    /**
+     * Gets the Namespace URI for this QName
+     *
+     * @return Namespace URI
+     */
+    public String getNamespaceURI() {
+        return namespaceURI;
+    }
+
+    /**
+     * Gets the Local part for this QName
+     *
+     * @return Local part
+     */
+    public String getLocalPart() {
+        return localPart;
+    }
+
+    /**
+     * Gets the Prefix for this QName
+     *
+     * @return Prefix
+     */
+    public String getPrefix() {
+        return prefix;
+    }
+
+    /**
+     * Returns a string representation of this QName
+     *
+     * @return  a string representation of the QName
+     */
+    public String toString() {
+
+        return ((namespaceURI == emptyString)
+                ? localPart
+                : '{' + namespaceURI + '}' + localPart);
+    }
+
+    /**
+     * Tests this QName for equality with another object.
+     * <p>
+     * If the given object is not a QName or is null then this method
+     * returns <tt>false</tt>.
+     * <p>
+     * For two QNames to be considered equal requires that both
+     * localPart and namespaceURI must be equal. This method uses
+     * <code>String.equals</code> to check equality of localPart
+     * and namespaceURI. Any class that extends QName is required
+     * to satisfy this equality contract.
+     * <p>
+     * This method satisfies the general contract of the <code>Object.equals</code> method.
+     *
+     * @param obj the reference object with which to compare
+     *
+     * @return <code>true</code> if the given object is identical to this
+     *      QName: <code>false</code> otherwise.
+     */
+    public final boolean equals(Object obj) {
+
+        if (obj == this) {
+            return true;
+        }
+
+        if (!(obj instanceof QName)) {
+            return false;
+        }
+
+        if ((namespaceURI == ((QName) obj).namespaceURI)
+                && (localPart == ((QName) obj).localPart)) {
+            return true;
+        }
+
+        return false;
+    }
+
+    /**
+     * Returns a QName holding the value of the specified String.
+     * <p>
+     * The string must be in the form returned by the QName.toString()
+     * method, i.e. "{namespaceURI}localPart", with the "{namespaceURI}"
+     * part being optional.
+     * <p>
+     * This method doesn't do a full validation of the resulting QName.
+     * In particular, it doesn't check that the resulting namespace URI
+     * is a legal URI (per RFC 2396 and RFC 2732), nor that the resulting
+     * local part is a legal NCName per the XML Namespaces specification.
+     *
+     * @param s the string to be parsed
+     * @throws java.lang.IllegalArgumentException If the specified String cannot be parsed as a QName
+     * @return QName corresponding to the given String
+     */
+    public static QName valueOf(String s) {
+
+        if ((s == null) || s.equals("")) {
+            throw new IllegalArgumentException("invalid QName literal");
+        }
+
+        if (s.charAt(0) == '{') {
+            int i = s.indexOf('}');
+
+            if (i == -1) {
+                throw new IllegalArgumentException("invalid QName literal");
+            }
+
+            if (i == s.length() - 1) {
+                throw new IllegalArgumentException("invalid QName literal");
+            } else {
+                return new QName(s.substring(1, i), s.substring(i + 1));
+            }
+        } else {
+            return new QName(s);
+        }
+    }
+
+    /**
+     * Returns a hash code value for this QName object. The hash code
+     * is based on both the localPart and namespaceURI parts of the
+     * QName. This method satisfies the  general contract of the
+     * <code>Object.hashCode</code> method.
+     *
+     * @return a hash code value for this Qname object
+     */
+    public final int hashCode() {
+        return namespaceURI.hashCode() ^ localPart.hashCode();
+    }
+
+    /**
+     * Ensure that deserialization properly interns the results.
+     * @param in the ObjectInputStream to be read
+     */
+    private void readObject(ObjectInputStream in) throws
+            IOException, ClassNotFoundException {
+        in.defaultReadObject();
+
+        namespaceURI = namespaceURI.intern();
+        localPart = localPart.intern();
+        prefix = prefix.intern();
+    }
+}
+
diff --git a/src/com/kenai/jbosh/RequestIDSequence.java b/src/com/kenai/jbosh/RequestIDSequence.java
new file mode 100644
index 0000000..14b1475
--- /dev/null
+++ b/src/com/kenai/jbosh/RequestIDSequence.java
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.security.SecureRandom;
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantLock;
+
+/**
+ * Request ID sequence generator.  This generator generates a random first
+ * RID and then manages the sequence from there on out.
+ */
+final class RequestIDSequence {
+
+    /**
+     * Maximum number of bits available for representing request IDs, according
+     * to the XEP-0124 spec.s
+     */
+    private static final int MAX_BITS = 53;
+
+    /**
+     * Bits devoted to incremented values.
+     */
+    private static final int INCREMENT_BITS = 32;
+
+    /**
+     * Minimum number of times the initial RID can be incremented before
+     * exceeding the maximum.
+     */
+    private static final long MIN_INCREMENTS = 1L << INCREMENT_BITS;
+
+    /**
+     * Max initial value. 
+     */
+    private static final long MAX_INITIAL = (1L << MAX_BITS) - MIN_INCREMENTS;
+
+    /**
+     * Max bits mask.
+     */
+    private static final long MASK = ~(Long.MAX_VALUE << MAX_BITS);
+
+    /**
+     * Random number generator.
+     */
+    private static final SecureRandom RAND = new SecureRandom();
+
+    /**
+     * Internal lock.
+     */
+    private static final Lock LOCK = new ReentrantLock();
+
+    /**
+     * The last reqest ID used, or &lt;= 0 if a new request ID needs to be
+     * generated.
+     */
+    private AtomicLong nextRequestID = new AtomicLong();
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent direct construction.
+     */
+    RequestIDSequence() {
+        nextRequestID = new AtomicLong(generateInitialValue());
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Public methods:
+
+    /**
+     * Calculates the next request ID value to use.  This number must be
+     * initialized such that it is unlikely to ever exceed 2 ^ 53, according
+     * to XEP-0124.
+     *
+     * @return next request ID value
+     */
+    public long getNextRID() {
+        return nextRequestID.getAndIncrement();
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Generates an initial RID value by generating numbers until a number is
+     * found which is smaller than the maximum allowed value and greater
+     * than zero.
+     *
+     * @return random initial value
+     */
+    private long generateInitialValue() {
+        long result;
+        LOCK.lock();
+        try {
+            do {
+                result = RAND.nextLong() & MASK;
+            } while (result > MAX_INITIAL);
+        } finally {
+            LOCK.unlock();
+        }
+        return result;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/ServiceLib.java b/src/com/kenai/jbosh/ServiceLib.java
new file mode 100644
index 0000000..07d0556
--- /dev/null
+++ b/src/com/kenai/jbosh/ServiceLib.java
@@ -0,0 +1,195 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.BufferedReader;
+import java.io.Closeable;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+/**
+ * Utility library for use in loading services using the Jar Service
+ * Provider Interface (Jar SPI).  This can be replaced once the minimum
+ * java rev moves beyond Java 5.
+ */
+final class ServiceLib {
+
+    /**
+     * Logger.
+     */
+    private static final Logger LOG =
+            Logger.getLogger(ServiceLib.class.getName());
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Prevent construction.
+     */
+    private ServiceLib() {
+        // Empty
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Package-private methods:
+
+    /**
+     * Probe for and select an implementation of the specified service
+     * type by using the a modified Jar SPI mechanism.  Modified in that
+     * the system properties will be checked to see if there is a value
+     * set for the naem of the class to be loaded.  If so, that value is
+     * treated as the class name of the first implementation class to be
+     * attempted to be loaded.  This provides a (unsupported) mechanism
+     * to insert other implementations.  Note that the supported mechanism
+     * is by properly ordering the classpath.
+     *
+     * @return service instance
+     * @throws IllegalStateException is no service implementations could be
+     *  instantiated
+     */
+    static <T> T loadService(Class<T> ofType) {
+        List<String> implClasses = loadServicesImplementations(ofType);
+        for (String implClass : implClasses) {
+            T result = attemptLoad(ofType, implClass);
+            if (result != null) {
+                if (LOG.isLoggable(Level.FINEST)) {
+                    LOG.finest("Selected " + ofType.getSimpleName()
+                            + " implementation: "
+                            + result.getClass().getName());
+                }
+                return result;
+            }
+        }
+        throw(new IllegalStateException(
+                "Could not load " + ofType.getName() + " implementation"));
+    }
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Private methods:
+
+    /**
+     * Generates a list of implementation class names by using
+     * the Jar SPI technique.  The order in which the class names occur
+     * in the service manifest is significant.
+     *
+     * @return list of all declared implementation class names
+     */
+    private static List<String> loadServicesImplementations(
+            final Class ofClass) {
+        List<String> result = new ArrayList<String>();
+
+        // Allow a sysprop to specify the first candidate
+        String override = System.getProperty(ofClass.getName());
+        if (override != null) {
+            result.add(override);
+        }
+
+        ClassLoader loader = ServiceLib.class.getClassLoader();
+        URL url = loader.getResource("META-INF/services/" + ofClass.getName());
+        InputStream inStream = null;
+        InputStreamReader reader = null;
+        BufferedReader bReader = null;
+        try {
+            inStream = url.openStream();
+            reader = new InputStreamReader(inStream);
+            bReader = new BufferedReader(reader);
+            String line;
+            while ((line = bReader.readLine()) != null) {
+                if (!line.matches("\\s*(#.*)?")) {
+                    // not a comment or blank line
+                    result.add(line.trim());
+                }
+            }
+        } catch (IOException iox) {
+            LOG.log(Level.WARNING,
+                    "Could not load services descriptor: " + url.toString(),
+                    iox);
+        } finally {
+            finalClose(bReader);
+            finalClose(reader);
+            finalClose(inStream);
+        }
+        return result;
+    }
+
+    /**
+     * Attempts to load the specified implementation class.
+     * Attempts will fail if - for example - the implementation depends
+     * on a class not found on the classpath.
+     *
+     * @param className implementation class to attempt to load
+     * @return service instance, or {@code null} if the instance could not be
+     *  loaded
+     */
+    private static <T> T attemptLoad(
+            final Class<T> ofClass,
+            final String className) {
+        if (LOG.isLoggable(Level.FINEST)) {
+            LOG.finest("Attempting service load: " + className);
+        }
+        Level level;
+        Exception thrown;
+        try {
+            Class clazz = Class.forName(className);
+            if (!ofClass.isAssignableFrom(clazz)) {
+                if (LOG.isLoggable(Level.WARNING)) {
+                    LOG.warning(clazz.getName() + " is not assignable to "
+                            + ofClass.getName());
+                }
+                return null;
+            }
+            return ofClass.cast(clazz.newInstance());
+        } catch (ClassNotFoundException ex) {
+            level = Level.FINEST;
+            thrown = ex;
+        } catch (InstantiationException ex) {
+            level = Level.WARNING;
+            thrown = ex;
+        } catch (IllegalAccessException ex) {
+            level = Level.WARNING;
+            thrown = ex;
+        }
+        LOG.log(level,
+                "Could not load " + ofClass.getSimpleName()
+                + " instance: " + className,
+                thrown);
+        return null;
+    }
+
+    /**
+     * Check and close a closeable object, trapping and ignoring any
+     * exception that might result.
+     *
+     * @param closeMe the thing to close
+     */
+    private static void finalClose(final Closeable closeMe) {
+        if (closeMe != null) {
+            try {
+                closeMe.close();
+            } catch (IOException iox) {
+                LOG.log(Level.FINEST, "Could not close: " + closeMe, iox);
+            }
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/StaticBody.java b/src/com/kenai/jbosh/StaticBody.java
new file mode 100644
index 0000000..fe225fb
--- /dev/null
+++ b/src/com/kenai/jbosh/StaticBody.java
@@ -0,0 +1,133 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Collections;
+import java.util.Map;
+
+/**
+ * Implementation of the {@code AbstractBody} class which allows for the
+ * definition of messages from pre-existing message content.  Instances of
+ * this class are based on the underlying data and therefore cannot be
+ * modified.  In order to obtain the wrapper element namespace and
+ * attribute information, the body content is partially parsed.
+ * <p/>
+ * This class does only minimal syntactic and semantic checking with respect
+ * to what the generated XML will look like.  It is up to the developer to
+ * protect against the definition of malformed XML messages when building
+ * instances of this class.
+ * <p/>
+ * Instances of this class are immutable and thread-safe.
+ */
+final class StaticBody extends AbstractBody {
+
+    /**
+     * Selected parser to be used to process raw XML messages.
+     */
+    private static final BodyParser PARSER =
+            new BodyParserXmlPull();
+
+    /**
+     * Size of the internal buffer when copying from a stream.
+     */
+    private static final int BUFFER_SIZE = 1024;
+
+    /**
+     * Map of all attributes to their values.
+     */
+    private final Map<BodyQName, String> attrs;
+
+    /**
+     * This body message in raw XML form.
+     */
+    private final String raw;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent direct construction.
+     */
+    private StaticBody(
+            final Map<BodyQName, String> attrMap,
+            final String rawXML) {
+        attrs = attrMap;
+        raw = rawXML;
+    }
+
+    /**
+     * Creates an instance which is initialized by reading a body
+     * message from the provided stream.
+     *
+     * @param inStream stream to read message XML from
+     * @return body instance
+     * @throws BOSHException on parse error
+     */
+    public static StaticBody fromStream(
+            final InputStream inStream)
+            throws BOSHException {
+        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
+        try {
+            byte[] buffer = new byte[BUFFER_SIZE];
+            int read;
+            do {
+                read = inStream.read(buffer);
+                if (read > 0) {
+                    byteOut.write(buffer, 0, read);
+                }
+            } while (read >= 0);
+        } catch (IOException iox) {
+            throw(new BOSHException(
+                    "Could not read body data", iox));
+        }
+        return fromString(byteOut.toString());
+    }
+
+    /**
+     * Creates an instance which is initialized by reading a body
+     * message from the provided raw XML string.
+     *
+     * @param rawXML raw message XML in string form
+     * @return body instance
+     * @throws BOSHException on parse error
+     */
+    public static StaticBody fromString(
+            final String rawXML)
+            throws BOSHException {
+        BodyParserResults results = PARSER.parse(rawXML);
+        return new StaticBody(results.getAttributes(), rawXML);
+    }
+
+
+    /**
+     * {@inheritDoc}
+     */
+    public Map<BodyQName, String> getAttributes() {
+        return Collections.unmodifiableMap(attrs);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public String toXML() {
+        return raw;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/TerminalBindingCondition.java b/src/com/kenai/jbosh/TerminalBindingCondition.java
new file mode 100644
index 0000000..0aecfd8
--- /dev/null
+++ b/src/com/kenai/jbosh/TerminalBindingCondition.java
@@ -0,0 +1,208 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Terminal binding conditions and their associated messages.
+ */
+final class TerminalBindingCondition {
+
+    /**
+     * Map of condition names to condition instances.
+     */
+    private static final Map<String, TerminalBindingCondition>
+            COND_TO_INSTANCE = new HashMap<String, TerminalBindingCondition>();
+
+    /**
+     * Map of HTTP response codes to condition instances.
+     */
+    private static final Map<Integer, TerminalBindingCondition>
+            CODE_TO_INSTANCE = new HashMap<Integer, TerminalBindingCondition>();
+
+    static final TerminalBindingCondition BAD_REQUEST =
+            createWithCode("bad-request", "The format of an HTTP header or "
+            + "binding element received from the client is unacceptable "
+            + "(e.g., syntax error).", Integer.valueOf(400));
+
+    static final TerminalBindingCondition HOST_GONE =
+            create("host-gone", "The target domain specified in the 'to' "
+            + "attribute or the target host or port specified in the 'route' "
+            + "attribute is no longer serviced by the connection manager.");
+
+    static final TerminalBindingCondition HOST_UNKNOWN =
+            create("host-unknown", "The target domain specified in the 'to' "
+            + "attribute or the target host or port specified in the 'route' "
+            + "attribute is unknown to the connection manager.");
+
+    static final TerminalBindingCondition IMPROPER_ADDRESSING =
+            create("improper-addressing", "The initialization element lacks a "
+            + "'to' or 'route' attribute (or the attribute has no value) but "
+            + "the connection manager requires one.");
+
+    static final TerminalBindingCondition INTERNAL_SERVER_ERROR =
+            create("internal-server-error", "The connection manager has "
+            + "experienced an internal error that prevents it from servicing "
+            + "the request.");
+
+    static final TerminalBindingCondition ITEM_NOT_FOUND =
+            createWithCode("item-not-found", "(1) 'sid' is not valid, (2) "
+            + "'stream' is not valid, (3) 'rid' is larger than the upper limit "
+            + "of the expected window, (4) connection manager is unable to "
+            + "resend response, (5) 'key' sequence is invalid.",
+            Integer.valueOf(404));
+
+    static final TerminalBindingCondition OTHER_REQUEST =
+            create("other-request", "Another request being processed at the "
+            + "same time as this request caused the session to terminate.");
+
+    static final TerminalBindingCondition POLICY_VIOLATION =
+            createWithCode("policy-violation", "The client has broken the "
+            + "session rules (polling too frequently, requesting too "
+            + "frequently, sending too many simultaneous requests).",
+            Integer.valueOf(403));
+
+    static final TerminalBindingCondition REMOTE_CONNECTION_FAILED =
+            create("remote-connection-failed", "The connection manager was "
+            + "unable to connect to, or unable to connect securely to, or has "
+            + "lost its connection to, the server.");
+
+    static final TerminalBindingCondition REMOTE_STREAM_ERROR =
+            create("remote-stream-error", "Encapsulated transport protocol "
+            + "error.");
+
+    static final TerminalBindingCondition SEE_OTHER_URI =
+            create("see-other-uri", "The connection manager does not operate "
+            + "at this URI (e.g., the connection manager accepts only SSL or "
+            + "TLS connections at some https: URI rather than the http: URI "
+            + "requested by the client).");
+
+    static final TerminalBindingCondition SYSTEM_SHUTDOWN =
+            create("system-shutdown", "The connection manager is being shut "
+            + "down. All active HTTP sessions are being terminated. No new "
+            + "sessions can be created.");
+
+    static final TerminalBindingCondition UNDEFINED_CONDITION =
+            create("undefined-condition", "Unknown or undefined error "
+            + "condition.");
+
+    /**
+     * Condition name.
+     */
+    private final String cond;
+
+    /**
+     * Descriptive message.
+     */
+    private final String msg;
+
+    /**
+     * Private constructor to pre
+     */
+    private TerminalBindingCondition(
+            final String condition,
+            final String message) {
+        cond = condition;
+        msg = message;
+    }
+    
+    /**
+     * Helper method to call the helper method to add entries.
+     */
+    private static TerminalBindingCondition create(
+            final String condition,
+            final String message) {
+        return createWithCode(condition, message, null);
+    }
+    
+    /**
+     * Helper method to add entries.
+     */
+    private static TerminalBindingCondition createWithCode(
+            final String condition,
+            final String message,
+            final Integer code) {
+        if (condition == null) {
+            throw(new IllegalArgumentException(
+                    "condition may not be null"));
+        }
+        if (message == null) {
+            throw(new IllegalArgumentException(
+                    "message may not be null"));
+        }
+        if (COND_TO_INSTANCE.get(condition) != null) {
+            throw(new IllegalStateException(
+                    "Multiple definitions of condition: " + condition));
+        }
+        TerminalBindingCondition result =
+                new TerminalBindingCondition(condition, message);
+        COND_TO_INSTANCE.put(condition, result);
+        if (code != null) {
+            if (CODE_TO_INSTANCE.get(code) != null) {
+                throw(new IllegalStateException(
+                        "Multiple definitions of code: " + code));
+            }
+            CODE_TO_INSTANCE.put(code, result);
+        }
+        return result;
+    }
+
+    /**
+     * Lookup the terminal binding condition instance with the condition
+     * name specified.
+     *
+     * @param condStr condition name
+     * @return terminal binding condition instance, or {@code null} if no
+     *  instance is known by the name specified
+     */
+    static TerminalBindingCondition forString(final String condStr) {
+        return COND_TO_INSTANCE.get(condStr);
+    }
+
+    /**
+     * Lookup the terminal binding condition instance associated with the
+     * HTTP response code specified.
+     *
+     * @param httpRespCode HTTP response code
+     * @return terminal binding condition instance, or {@code null} if no
+     *  instance is known by the response code specified
+     */
+    static TerminalBindingCondition forHTTPResponseCode(final int httpRespCode) {
+        return CODE_TO_INSTANCE.get(Integer.valueOf(httpRespCode));
+    }
+
+    /**
+     * Get the name of the condition.
+     *
+     * @return condition name
+     */
+    String getCondition() {
+        return cond;
+    }
+
+    /**
+     * Get the human readable error message associated with this condition.
+     *
+     * @return error message
+     */
+    String getMessage() {
+        return msg;
+    }
+
+}
diff --git a/src/com/kenai/jbosh/ZLIBCodec.java b/src/com/kenai/jbosh/ZLIBCodec.java
new file mode 100644
index 0000000..20844ad
--- /dev/null
+++ b/src/com/kenai/jbosh/ZLIBCodec.java
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2009 Mike Cumings
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.kenai.jbosh;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.zip.DeflaterOutputStream;
+import java.util.zip.InflaterInputStream;
+
+/**
+ * Codec methods for compressing and uncompressing using ZLIB.
+ */
+final class ZLIBCodec {
+
+    /**
+     * Size of the internal buffer when decoding.
+     */
+    private static final int BUFFER_SIZE = 512;
+
+    ///////////////////////////////////////////////////////////////////////////
+    // Constructors:
+
+    /**
+     * Prevent construction.
+     */
+    private ZLIBCodec() {
+        // Empty
+    }
+
+    /**
+     * Returns the name of the codec.
+     *
+     * @return string name of the codec (i.e., "deflate")
+     */
+    public static String getID() {
+        return "deflate";
+    }
+
+    /**
+     * Compress/encode the data provided using the ZLIB format.
+     *
+     * @param data data to compress
+     * @return compressed data
+     * @throws IOException on compression failure
+     */
+    public static byte[] encode(final byte[] data) throws IOException {
+        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
+        DeflaterOutputStream deflateOut = null;
+        try {
+            deflateOut = new DeflaterOutputStream(byteOut);
+            deflateOut.write(data);
+            deflateOut.close();
+            byteOut.close();
+            return byteOut.toByteArray();
+        } finally {
+            deflateOut.close();
+            byteOut.close();
+        }
+    }
+
+    /**
+     * Uncompress/decode the data provided using the ZLIB format.
+     *
+     * @param data data to uncompress
+     * @return uncompressed data
+     * @throws IOException on decompression failure
+     */
+    public static byte[] decode(final byte[] compressed) throws IOException {
+        ByteArrayInputStream byteIn = new ByteArrayInputStream(compressed);
+        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
+        InflaterInputStream inflaterIn = null;
+        try {
+            inflaterIn = new InflaterInputStream(byteIn);
+            int read;
+            byte[] buffer = new byte[BUFFER_SIZE];
+            do {
+                read = inflaterIn.read(buffer);
+                if (read > 0) {
+                    byteOut.write(buffer, 0, read);
+                }
+            } while (read >= 0);
+            return byteOut.toByteArray();
+        } finally {
+            inflaterIn.close();
+            byteOut.close();
+        }
+    }
+
+}
diff --git a/src/com/kenai/jbosh/package.html b/src/com/kenai/jbosh/package.html
new file mode 100644
index 0000000..77a1924
--- /dev/null
+++ b/src/com/kenai/jbosh/package.html
@@ -0,0 +1,8 @@
+<html>
+    <body>
+        Core classes of the JBOSH API.
+        <p/>
+        Users of the client portion of the API should start by reading
+        up on the <code>BOSHClient</code> documentation.
+    </body>
+</html>
\ No newline at end of file
diff --git a/src/com/novell/sasl/client/DigestChallenge.java b/src/com/novell/sasl/client/DigestChallenge.java
new file mode 100644
index 0000000..90e6247
--- /dev/null
+++ b/src/com/novell/sasl/client/DigestChallenge.java
@@ -0,0 +1,393 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/DigestChallenge.java,v 1.3 2005/01/17 15:00:54 sunilk Exp $
+ *
+ * Copyright (C) 2003 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+import java.util.*;
+import org.apache.harmony.javax.security.sasl.*;
+
+/**
+ * Implements the DigestChallenge class which will be used by the
+ * DigestMD5SaslClient class
+ */
+class DigestChallenge extends Object
+{
+    public static final int QOP_AUTH           =    0x01;
+    public static final int QOP_AUTH_INT       =    0x02;
+    public static final int QOP_AUTH_CONF       =    0x04;
+    public static final int QOP_UNRECOGNIZED   =    0x08;
+
+    private static final int CIPHER_3DES          = 0x01;
+    private static final int CIPHER_DES           = 0x02;
+    private static final int CIPHER_RC4_40        = 0x04;
+    private static final int CIPHER_RC4           = 0x08;
+    private static final int CIPHER_RC4_56        = 0x10;
+    private static final int CIPHER_UNRECOGNIZED  = 0x20;
+    private static final int CIPHER_RECOGNIZED_MASK =
+     CIPHER_3DES | CIPHER_DES | CIPHER_RC4_40 | CIPHER_RC4 | CIPHER_RC4_56;
+
+    private ArrayList m_realms;
+    private String    m_nonce;
+    private int       m_qop;
+    private boolean   m_staleFlag;
+    private int       m_maxBuf;
+    private String    m_characterSet;
+    private String    m_algorithm;
+    private int       m_cipherOptions;
+
+    DigestChallenge(
+        byte[] challenge)
+            throws SaslException
+    {
+        m_realms = new ArrayList(5);
+        m_nonce = null;
+        m_qop = 0;
+        m_staleFlag = false;
+        m_maxBuf = -1;
+        m_characterSet = null;
+        m_algorithm = null;
+        m_cipherOptions = 0;
+
+        DirectiveList dirList = new DirectiveList(challenge);
+        try
+        {
+            dirList.parseDirectives();
+            checkSemantics(dirList);
+        }
+        catch (SaslException e)
+        {
+        }
+    }
+
+    /**
+     * Checks the semantics of the directives in the directive list as parsed
+     * from the digest challenge byte array.
+     *
+     * @param dirList  the list of directives parsed from the digest challenge
+     *
+     * @exception SaslException   If a semantic error occurs
+     */
+    void checkSemantics(
+        DirectiveList dirList) throws SaslException
+    {
+    Iterator        directives = dirList.getIterator();
+    ParsedDirective directive;
+    String          name;
+
+    while (directives.hasNext())
+    {
+        directive = (ParsedDirective)directives.next();
+        name = directive.getName();
+        if (name.equals("realm"))
+            handleRealm(directive);
+        else if (name.equals("nonce"))
+            handleNonce(directive);
+        else if (name.equals("qop"))
+            handleQop(directive);
+        else if (name.equals("maxbuf"))
+            handleMaxbuf(directive);
+        else if (name.equals("charset"))
+            handleCharset(directive);
+        else if (name.equals("algorithm"))
+            handleAlgorithm(directive);
+        else if (name.equals("cipher"))
+            handleCipher(directive);
+        else if (name.equals("stale"))
+            handleStale(directive);
+    }
+
+    /* post semantic check */
+    if (-1 == m_maxBuf)
+        m_maxBuf = 65536;
+
+    if (m_qop == 0)
+        m_qop = QOP_AUTH;
+    else if ( (m_qop & QOP_AUTH) != QOP_AUTH )
+        throw new SaslException("Only qop-auth is supported by client");
+    else if ( ((m_qop & QOP_AUTH_CONF) == QOP_AUTH_CONF) &&
+              (0 == (m_cipherOptions & CIPHER_RECOGNIZED_MASK)) )
+        throw new SaslException("Invalid cipher options");
+    else if (null == m_nonce)
+        throw new SaslException("Missing nonce directive");
+    else if (m_staleFlag)
+        throw new SaslException("Unexpected stale flag");
+    else if ( null == m_algorithm )
+        throw new SaslException("Missing algorithm directive");
+    }
+
+    /**
+     * This function implements the semenatics of the nonce directive.
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException   If an error occurs due to too many nonce
+     *                             values
+     */
+    void handleNonce(
+        ParsedDirective  pd) throws SaslException
+    {
+        if (null != m_nonce)
+            throw new SaslException("Too many nonce values.");
+
+        m_nonce = pd.getValue();
+    }
+
+    /**
+     * This function implements the semenatics of the realm directive.
+     *
+     * @param      pd   ParsedDirective
+     */
+    void handleRealm(
+        ParsedDirective  pd)
+    {
+        m_realms.add(pd.getValue());
+    }
+
+    /**
+     * This function implements the semenatics of the qop (quality of protection)
+     * directive. The value of the qop directive is as defined below:
+     *      qop-options =     "qop" "=" <"> qop-list <">
+     *      qop-list    =     1#qop-value
+     *      qop-value    =     "auth" | "auth-int"  | "auth-conf" | token
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException   If an error occurs due to too many qop
+     *                             directives
+     */
+    void handleQop(
+        ParsedDirective  pd) throws SaslException
+    {
+        String       token;
+        TokenParser  parser;
+
+        if (m_qop != 0)
+            throw new SaslException("Too many qop directives.");
+
+        parser = new TokenParser(pd.getValue());
+        for (token = parser.parseToken();
+             token != null;
+             token = parser.parseToken())
+        {
+            if (token.equals("auth"))
+                  m_qop |= QOP_AUTH;
+              else if (token.equals("auth-int"))
+                  m_qop |= QOP_AUTH_INT;
+            else if (token.equals("auth-conf"))
+                m_qop |= QOP_AUTH_CONF;
+            else
+                m_qop |= QOP_UNRECOGNIZED;
+        }
+    }
+
+    /**
+     * This function implements the semenatics of the Maxbuf directive.
+     * the value is defined as: 1*DIGIT
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException If an error occur    
+     */
+    void handleMaxbuf(
+        ParsedDirective  pd) throws SaslException
+    {
+        if (-1 != m_maxBuf) /*it's initialized to -1 */
+            throw new SaslException("Too many maxBuf directives.");
+
+        m_maxBuf = Integer.parseInt(pd.getValue());
+
+        if (0 == m_maxBuf)
+            throw new SaslException("Max buf value must be greater than zero.");
+    }
+
+    /**
+     * This function implements the semenatics of the charset directive.
+     * the value is defined as: 1*DIGIT
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException If an error occurs dur to too many charset
+     *                           directives or Invalid character encoding
+     *                           directive
+     */
+    void handleCharset(
+        ParsedDirective  pd) throws SaslException
+    {
+        if (null != m_characterSet)
+            throw new SaslException("Too many charset directives.");
+
+        m_characterSet = pd.getValue();
+
+        if (!m_characterSet.equals("utf-8"))
+            throw new SaslException("Invalid character encoding directive");
+    }
+
+    /**
+     * This function implements the semenatics of the charset directive.
+     * the value is defined as: 1*DIGIT
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException If an error occurs due to too many algorith
+     *                           directive or Invalid algorithm directive
+     *                           value
+     */
+    void handleAlgorithm(
+        ParsedDirective  pd) throws SaslException
+    {
+        if (null != m_algorithm)
+            throw new SaslException("Too many algorithm directives.");
+
+          m_algorithm = pd.getValue();
+
+        if (!"md5-sess".equals(m_algorithm))
+            throw new SaslException("Invalid algorithm directive value: " +
+                                    m_algorithm);
+    }
+
+    /**
+     * This function implements the semenatics of the cipher-opts directive
+     * directive. The value of the qop directive is as defined below:
+     *      qop-options =     "qop" "=" <"> qop-list <">
+     *      qop-list    =     1#qop-value
+     *      qop-value    =     "auth" | "auth-int"  | "auth-conf" | token
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException If an error occurs due to Too many cipher
+     *                           directives 
+     */
+    void handleCipher(
+        ParsedDirective  pd) throws SaslException
+    {
+        String  token;
+        TokenParser parser;
+
+        if (0 != m_cipherOptions)
+            throw new SaslException("Too many cipher directives.");
+
+        parser = new TokenParser(pd.getValue());
+        token = parser.parseToken();
+        for (token = parser.parseToken();
+             token != null;
+             token = parser.parseToken())
+        {
+              if ("3des".equals(token))
+                  m_cipherOptions |= CIPHER_3DES;
+              else if ("des".equals(token))
+                  m_cipherOptions |= CIPHER_DES;
+            else if ("rc4-40".equals(token))
+                m_cipherOptions |= CIPHER_RC4_40;
+            else if ("rc4".equals(token))
+                m_cipherOptions |= CIPHER_RC4;
+            else if ("rc4-56".equals(token))
+                m_cipherOptions |= CIPHER_RC4_56;
+            else
+                m_cipherOptions |= CIPHER_UNRECOGNIZED;
+        }
+
+        if (m_cipherOptions == 0)
+            m_cipherOptions = CIPHER_UNRECOGNIZED;
+    }
+
+    /**
+     * This function implements the semenatics of the stale directive.
+     *
+     * @param      pd   ParsedDirective
+     *
+     * @exception  SaslException If an error occurs due to Too many stale
+     *                           directives or Invalid stale directive value
+     */
+    void handleStale(
+        ParsedDirective  pd) throws SaslException
+    {
+        if (false != m_staleFlag)
+            throw new SaslException("Too many stale directives.");
+
+        if ("true".equals(pd.getValue()))
+            m_staleFlag = true;
+        else
+            throw new SaslException("Invalid stale directive value: " +
+                                    pd.getValue());
+    }
+
+    /**
+     * Return the list of the All the Realms
+     *
+     * @return  List of all the realms 
+     */
+    public ArrayList getRealms()
+    {
+        return m_realms;
+    }
+
+    /**
+     * @return Returns the Nonce
+     */
+    public String getNonce()
+    {
+        return m_nonce;
+    }
+
+    /**
+     * Return the quality-of-protection
+     * 
+     * @return The quality-of-protection
+     */
+    public int getQop()
+    {
+        return m_qop;
+    }
+
+    /**
+     * @return The state of the Staleflag
+     */
+    public boolean getStaleFlag()
+    {
+        return m_staleFlag;
+    }
+
+    /**
+     * @return The Maximum Buffer value
+     */
+    public int getMaxBuf()
+    {
+        return m_maxBuf;
+    }
+
+    /**
+     * @return character set values as string
+     */
+    public String getCharacterSet()
+    {
+        return m_characterSet;
+    }
+
+    /**
+     * @return The String value of the algorithm
+     */
+    public String getAlgorithm()
+    {
+        return m_algorithm;
+    }
+
+    /**
+     * @return The cipher options
+     */
+    public int getCipherOptions()
+    {
+        return m_cipherOptions;
+    }
+}
+
diff --git a/src/com/novell/sasl/client/DigestMD5SaslClient.java b/src/com/novell/sasl/client/DigestMD5SaslClient.java
new file mode 100644
index 0000000..141c96b
--- /dev/null
+++ b/src/com/novell/sasl/client/DigestMD5SaslClient.java
@@ -0,0 +1,820 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/DigestMD5SaslClient.java,v 1.4 2005/01/17 15:00:54 sunilk Exp $
+ *
+ * Copyright (C) 2003 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+import org.apache.harmony.javax.security.sasl.*;
+import org.apache.harmony.javax.security.auth.callback.*;
+import java.security.SecureRandom;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.io.UnsupportedEncodingException;
+import java.io.IOException;
+import java.util.*;
+
+/**
+ * Implements the Client portion of DigestMD5 Sasl mechanism.
+ */
+public class DigestMD5SaslClient implements SaslClient
+{
+    private String           m_authorizationId = "";
+    private String           m_protocol = "";
+    private String           m_serverName = "";
+    private Map              m_props;
+    private CallbackHandler  m_cbh;
+    private int              m_state;
+    private String           m_qopValue = "";
+    private char[]              m_HA1 = null;
+    private String           m_digestURI;
+    private DigestChallenge  m_dc;
+    private String           m_clientNonce = "";
+    private String           m_realm = "";
+    private String           m_name = "";
+
+    private static final int   STATE_INITIAL = 0;
+    private static final int   STATE_DIGEST_RESPONSE_SENT = 1;
+    private static final int   STATE_VALID_SERVER_RESPONSE = 2;
+    private static final int   STATE_INVALID_SERVER_RESPONSE = 3;
+    private static final int   STATE_DISPOSED = 4;
+
+    private static final int   NONCE_BYTE_COUNT = 32;
+    private static final int   NONCE_HEX_COUNT = 2*NONCE_BYTE_COUNT;
+
+    private static final String DIGEST_METHOD = "AUTHENTICATE";
+
+    /**
+     * Creates an DigestMD5SaslClient object using the parameters supplied.
+     * Assumes that the QOP, STRENGTH, and SERVER_AUTH properties are
+     * contained in props
+     *
+     * @param authorizationId  The possibly null protocol-dependent
+     *                     identification to be used for authorization. If
+     *                     null or empty, the server derives an authorization
+     *                     ID from the client's authentication credentials.
+     *                     When the SASL authentication completes
+     *                     successfully, the specified entity is granted
+     *                     access.
+     *
+     * @param protocol     The non-null string name of the protocol for which
+     *                     the authentication is being performed (e.g. "ldap")
+     *
+     * @param serverName   The non-null fully qualified host name of the server
+     *                     to authenticate to
+     *
+     * @param props        The possibly null set of properties used to select
+     *                     the SASL mechanism and to configure the
+     *                     authentication exchange of the selected mechanism.
+     *                     See the Sasl class for a list of standard properties.
+     *                     Other, possibly mechanism-specific, properties can
+     *                     be included. Properties not relevant to the selected
+     *                     mechanism are ignored.
+     *
+     * @param cbh          The possibly null callback handler to used by the
+     *                     SASL mechanisms to get further information from the
+     *                     application/library to complete the authentication.
+     *                     For example, a SASL mechanism might require the
+     *                     authentication ID, password and realm from the
+     *                     caller. The authentication ID is requested by using
+     *                     a NameCallback. The password is requested by using
+     *                     a PasswordCallback. The realm is requested by using
+     *                     a RealmChoiceCallback if there is a list of realms
+     *                     to choose from, and by using a RealmCallback if the
+     *                     realm must be entered.
+     *
+     * @return            A possibly null SaslClient created using the
+     *                     parameters supplied. If null, this factory cannot
+     *                     produce a SaslClient using the parameters supplied.
+     *
+     * @exception SaslException  If a SaslClient instance cannot be created
+     *                     because of an error
+     */
+    public static SaslClient getClient(
+        String          authorizationId,
+        String          protocol,
+        String          serverName,
+        Map             props,
+        CallbackHandler cbh)
+    {
+        String desiredQOP = (String)props.get(Sasl.QOP);
+        String desiredStrength = (String)props.get(Sasl.STRENGTH);
+        String serverAuth = (String)props.get(Sasl.SERVER_AUTH);
+
+        //only support qop equal to auth
+        if ((desiredQOP != null) && !"auth".equals(desiredQOP))
+            return null;
+
+        //doesn't support server authentication
+        if ((serverAuth != null) && !"false".equals(serverAuth))
+            return null;
+
+        //need a callback handler to get the password
+        if (cbh == null)
+            return null;
+
+        return new DigestMD5SaslClient(authorizationId, protocol,
+                                       serverName, props, cbh);
+    }
+
+    /**
+     * Creates an DigestMD5SaslClient object using the parameters supplied.
+     * Assumes that the QOP, STRENGTH, and SERVER_AUTH properties are
+     * contained in props
+     *
+     * @param authorizationId  The possibly null protocol-dependent
+     *                     identification to be used for authorization. If
+     *                     null or empty, the server derives an authorization
+     *                     ID from the client's authentication credentials.
+     *                     When the SASL authentication completes
+     *                     successfully, the specified entity is granted
+     *                     access.
+     *
+     * @param protocol     The non-null string name of the protocol for which
+     *                     the authentication is being performed (e.g. "ldap")
+     *
+     * @param serverName   The non-null fully qualified host name of the server
+     *                     to authenticate to
+     *
+     * @param props        The possibly null set of properties used to select
+     *                     the SASL mechanism and to configure the
+     *                     authentication exchange of the selected mechanism.
+     *                     See the Sasl class for a list of standard properties.
+     *                     Other, possibly mechanism-specific, properties can
+     *                     be included. Properties not relevant to the selected
+     *                     mechanism are ignored.
+     *
+     * @param cbh          The possibly null callback handler to used by the
+     *                     SASL mechanisms to get further information from the
+     *                     application/library to complete the authentication.
+     *                     For example, a SASL mechanism might require the
+     *                     authentication ID, password and realm from the
+     *                     caller. The authentication ID is requested by using
+     *                     a NameCallback. The password is requested by using
+     *                     a PasswordCallback. The realm is requested by using
+     *                     a RealmChoiceCallback if there is a list of realms
+     *                     to choose from, and by using a RealmCallback if the
+     *                     realm must be entered.
+     *
+     */
+    private  DigestMD5SaslClient(
+        String          authorizationId,
+        String          protocol,
+        String          serverName,
+        Map             props,
+        CallbackHandler cbh)
+    {
+        m_authorizationId = authorizationId;
+        m_protocol = protocol;
+        m_serverName = serverName;
+        m_props = props;
+        m_cbh = cbh;
+
+        m_state = STATE_INITIAL;
+    }
+
+    /**
+     * Determines if this mechanism has an optional initial response. If true,
+     * caller should call evaluateChallenge() with an empty array to get the
+     * initial response.
+     *
+     * @return  true if this mechanism has an initial response
+     */
+    public boolean hasInitialResponse()
+    {
+        return false;
+    }
+
+    /**
+     * Determines if the authentication exchange has completed. This method
+     * may be called at any time, but typically, it will not be called until
+     * the caller has received indication from the server (in a protocol-
+     * specific manner) that the exchange has completed.
+     *
+     * @return  true if the authentication exchange has completed;
+     *           false otherwise.
+     */
+    public boolean isComplete()
+    {
+        if ((m_state == STATE_VALID_SERVER_RESPONSE) ||
+            (m_state == STATE_INVALID_SERVER_RESPONSE) ||
+            (m_state == STATE_DISPOSED))
+            return true;
+        else
+            return false;
+    }
+
+    /**
+     * Unwraps a byte array received from the server. This method can be called
+     * only after the authentication exchange has completed (i.e., when
+     * isComplete() returns true) and only if the authentication exchange has
+     * negotiated integrity and/or privacy as the quality of protection;
+     * otherwise, an IllegalStateException is thrown.
+     *
+     * incoming is the contents of the SASL buffer as defined in RFC 2222
+     * without the leading four octet field that represents the length.
+     * offset and len specify the portion of incoming to use.
+     *
+     * @param incoming   A non-null byte array containing the encoded bytes
+     *                   from the server
+     * @param offset     The starting position at incoming of the bytes to use
+     *
+     * @param len        The number of bytes from incoming to use
+     *
+     * @return           A non-null byte array containing the decoded bytes
+     *
+     */
+    public byte[] unwrap(
+        byte[] incoming,
+        int    offset,
+        int    len)
+            throws SaslException
+    {
+        throw new IllegalStateException(
+         "unwrap: QOP has neither integrity nor privacy>");
+    }
+
+    /**
+     * Wraps a byte array to be sent to the server. This method can be called
+     * only after the authentication exchange has completed (i.e., when
+     * isComplete() returns true) and only if the authentication exchange has
+     * negotiated integrity and/or privacy as the quality of protection;
+     * otherwise, an IllegalStateException is thrown.
+     *
+     * The result of this method will make up the contents of the SASL buffer as
+     * defined in RFC 2222 without the leading four octet field that represents
+     * the length. offset and len specify the portion of outgoing to use.
+     *
+     * @param outgoing   A non-null byte array containing the bytes to encode
+     * @param offset     The starting position at outgoing of the bytes to use
+     * @param len        The number of bytes from outgoing to use
+     *
+     * @return A non-null byte array containing the encoded bytes
+     *
+     * @exception SaslException  if incoming cannot be successfully unwrapped.
+     *
+     * @exception IllegalStateException   if the authentication exchange has
+     *                   not completed, or if the negotiated quality of
+     *                   protection has neither integrity nor privacy.
+     */
+    public byte[] wrap(
+        byte[]  outgoing,
+        int     offset,
+        int     len)
+            throws SaslException
+    {
+        throw new IllegalStateException(
+         "wrap: QOP has neither integrity nor privacy>");
+    }
+
+    /**
+     * Retrieves the negotiated property. This method can be called only after
+     * the authentication exchange has completed (i.e., when isComplete()
+     * returns true); otherwise, an IllegalStateException is thrown.
+     *
+     * @param propName   The non-null property name
+     *
+     * @return  The value of the negotiated property. If null, the property was
+     *          not negotiated or is not applicable to this mechanism.
+     *
+     * @exception IllegalStateException   if this authentication exchange has
+     *                                    not completed
+     */
+    public Object getNegotiatedProperty(
+        String propName)
+    {
+        if (m_state != STATE_VALID_SERVER_RESPONSE)
+            throw new IllegalStateException(
+             "getNegotiatedProperty: authentication exchange not complete.");
+
+        if (Sasl.QOP.equals(propName))
+            return "auth";
+        else
+            return null;
+    }
+
+    /**
+     * Disposes of any system resources or security-sensitive information the
+     * SaslClient might be using. Invoking this method invalidates the
+     * SaslClient instance. This method is idempotent.
+     *
+     * @exception SaslException  if a problem was encountered while disposing
+     *                           of the resources
+     */
+    public void dispose()
+            throws SaslException
+    {
+        if (m_state != STATE_DISPOSED)
+        {
+            m_state = STATE_DISPOSED;
+        }
+    }
+
+    /**
+     * Evaluates the challenge data and generates a response. If a challenge
+     * is received from the server during the authentication process, this
+     * method is called to prepare an appropriate next response to submit to
+     * the server.
+     *
+     * @param challenge  The non-null challenge sent from the server. The
+     *                   challenge array may have zero length.
+     *
+     * @return    The possibly null reponse to send to the server. It is null
+     *            if the challenge accompanied a "SUCCESS" status and the
+     *            challenge only contains data for the client to update its
+     *            state and no response needs to be sent to the server.
+     *            The response is a zero-length byte array if the client is to
+     *            send a response with no data.
+     *
+     * @exception SaslException   If an error occurred while processing the
+     *                            challenge or generating a response.
+     */
+    public byte[] evaluateChallenge(
+        byte[] challenge)
+            throws SaslException
+    {
+        byte[] response = null;
+
+        //printState();
+        switch (m_state)
+        {
+        case STATE_INITIAL:
+            if (challenge.length == 0)
+                throw new SaslException("response = byte[0]");
+            else
+                try
+                {
+                    response = createDigestResponse(challenge).
+                                                           getBytes("UTF-8");
+                    m_state = STATE_DIGEST_RESPONSE_SENT;
+                }
+                catch (java.io.UnsupportedEncodingException e)
+                {
+                    throw new SaslException(
+                     "UTF-8 encoding not suppported by platform", e);
+                }
+            break;
+        case STATE_DIGEST_RESPONSE_SENT:
+            if (checkServerResponseAuth(challenge))
+                m_state = STATE_VALID_SERVER_RESPONSE;
+            else
+            {
+                m_state = STATE_INVALID_SERVER_RESPONSE;
+                throw new SaslException("Could not validate response-auth " +
+                                        "value from server");
+            }
+            break;
+        case STATE_VALID_SERVER_RESPONSE:
+        case STATE_INVALID_SERVER_RESPONSE:
+            throw new SaslException("Authentication sequence is complete");
+        case STATE_DISPOSED:
+            throw new SaslException("Client has been disposed");
+        default:
+            throw new SaslException("Unknown client state.");
+        }
+
+        return response;
+    }
+
+    /**
+     * This function takes a 16 byte binary md5-hash value and creates a 32
+     * character (plus    a terminating null character) hex-digit 
+     * representation of binary data.
+     *
+     * @param hash  16 byte binary md5-hash value in bytes
+     * 
+     * @return   32 character (plus    a terminating null character) hex-digit
+     *           representation of binary data.
+     */
+    char[] convertToHex(
+        byte[] hash)
+    {
+        int          i;
+        byte         j;
+        byte         fifteen = 15;
+        char[]      hex = new char[32];
+
+        for (i = 0; i < 16; i++)
+        {
+            //convert value of top 4 bits to hex char
+            hex[i*2] = getHexChar((byte)((hash[i] & 0xf0) >> 4));
+            //convert value of bottom 4 bits to hex char
+            hex[(i*2)+1] = getHexChar((byte)(hash[i] & 0x0f));
+        }
+
+        return hex;
+    }
+
+    /**
+     * Calculates the HA1 portion of the response
+     *
+     * @param  algorithm   Algorith to use.
+     * @param  userName    User being authenticated
+     * @param  realm       realm information
+     * @param  password    password of teh user
+     * @param  nonce       nonce value
+     * @param  clientNonce Clients Nonce value
+     *
+     * @return  HA1 portion of the response in a character array
+     *
+     * @exception SaslException  If an error occurs
+     */
+    char[] DigestCalcHA1(
+        String   algorithm,
+        String   userName,
+        String   realm,
+        String   password,
+        String   nonce,
+        String   clientNonce) throws SaslException
+    {
+        byte[]        hash;
+
+        try
+        {
+            MessageDigest md = MessageDigest.getInstance("MD5");
+
+            md.update(userName.getBytes("UTF-8"));
+            md.update(":".getBytes("UTF-8"));
+            md.update(realm.getBytes("UTF-8"));
+            md.update(":".getBytes("UTF-8"));
+            md.update(password.getBytes("UTF-8"));
+            hash = md.digest();
+
+            if ("md5-sess".equals(algorithm))
+            {
+                md.update(hash);
+                md.update(":".getBytes("UTF-8"));
+                md.update(nonce.getBytes("UTF-8"));
+                md.update(":".getBytes("UTF-8"));
+                md.update(clientNonce.getBytes("UTF-8"));
+                hash = md.digest();
+            }
+        }
+        catch(NoSuchAlgorithmException e)
+        {
+            throw new SaslException("No provider found for MD5 hash", e);
+        }
+        catch(UnsupportedEncodingException e)
+        {
+            throw new SaslException(
+             "UTF-8 encoding not supported by platform.", e);
+        }
+
+        return convertToHex(hash);
+    }
+
+
+    /**
+     * This function calculates the response-value of the response directive of
+     * the digest-response as documented in RFC 2831
+     *
+     * @param  HA1           H(A1)
+     * @param  serverNonce   nonce from server
+     * @param  nonceCount    8 hex digits
+     * @param  clientNonce   client nonce 
+     * @param  qop           qop-value: "", "auth", "auth-int"
+     * @param  method        method from the request
+     * @param  digestUri     requested URL
+     * @param  clientResponseFlag request-digest or response-digest
+     *
+     * @return Response-value of the response directive of the digest-response
+     *
+     * @exception SaslException  If an error occurs
+     */
+    char[] DigestCalcResponse(
+        char[]      HA1,            /* H(A1) */
+        String      serverNonce,    /* nonce from server */
+        String      nonceCount,     /* 8 hex digits */
+        String      clientNonce,    /* client nonce */
+        String      qop,            /* qop-value: "", "auth", "auth-int" */
+        String      method,         /* method from the request */
+        String      digestUri,      /* requested URL */
+        boolean     clientResponseFlag) /* request-digest or response-digest */
+            throws SaslException
+    {
+        byte[]             HA2;
+        byte[]             respHash;
+        char[]             HA2Hex;
+
+        // calculate H(A2)
+        try
+        {
+            MessageDigest md = MessageDigest.getInstance("MD5");
+            if (clientResponseFlag)
+                  md.update(method.getBytes("UTF-8"));
+            md.update(":".getBytes("UTF-8"));
+            md.update(digestUri.getBytes("UTF-8"));
+            if ("auth-int".equals(qop))
+            {
+                md.update(":".getBytes("UTF-8"));
+                md.update("00000000000000000000000000000000".getBytes("UTF-8"));
+            }
+            HA2 = md.digest();
+            HA2Hex = convertToHex(HA2);
+
+            // calculate response
+            md.update(new String(HA1).getBytes("UTF-8"));
+            md.update(":".getBytes("UTF-8"));
+            md.update(serverNonce.getBytes("UTF-8"));
+            md.update(":".getBytes("UTF-8"));
+            if (qop.length() > 0)
+            {
+                md.update(nonceCount.getBytes("UTF-8"));
+                md.update(":".getBytes("UTF-8"));
+                md.update(clientNonce.getBytes("UTF-8"));
+                md.update(":".getBytes("UTF-8"));
+                md.update(qop.getBytes("UTF-8"));
+                md.update(":".getBytes("UTF-8"));
+            }
+            md.update(new String(HA2Hex).getBytes("UTF-8"));
+            respHash = md.digest();
+        }
+        catch(NoSuchAlgorithmException e)
+        {
+            throw new SaslException("No provider found for MD5 hash", e);
+        }
+        catch(UnsupportedEncodingException e)
+        {
+            throw new SaslException(
+             "UTF-8 encoding not supported by platform.", e);
+        }
+
+        return convertToHex(respHash);
+    }
+
+
+    /**
+     * Creates the intial response to be sent to the server.
+     *
+     * @param challenge  Challenge in bytes recived form the Server
+     *
+     * @return Initial response to be sent to the server
+     */
+    private String createDigestResponse(
+        byte[] challenge)
+            throws SaslException
+    {
+        char[]            response;
+        StringBuffer    digestResponse = new StringBuffer(512);
+        int             realmSize;
+
+        m_dc = new DigestChallenge(challenge);
+
+        m_digestURI = m_protocol + "/" + m_serverName;
+
+        if ((m_dc.getQop() & DigestChallenge.QOP_AUTH)
+            == DigestChallenge.QOP_AUTH )
+            m_qopValue = "auth";
+        else
+            throw new SaslException("Client only supports qop of 'auth'");
+
+        //get call back information
+        Callback[] callbacks = new Callback[3];
+        ArrayList realms = m_dc.getRealms();
+        realmSize = realms.size();
+        if (realmSize == 0)
+        {
+            callbacks[0] = new RealmCallback("Realm");
+        }
+        else if (realmSize == 1)
+        {
+            callbacks[0] = new RealmCallback("Realm", (String)realms.get(0));
+        }
+        else
+        {
+            callbacks[0] =
+             new RealmChoiceCallback(
+                         "Realm",
+                         (String[])realms.toArray(new String[realmSize]),
+                          0,      //the default choice index
+                          false); //no multiple selections
+        }
+
+        callbacks[1] = new PasswordCallback("Password", false); 
+        //false = no echo
+
+        if (m_authorizationId == null || m_authorizationId.length() == 0)
+            callbacks[2] = new NameCallback("Name");
+        else
+            callbacks[2] = new NameCallback("Name", m_authorizationId);
+
+        try
+        {
+            m_cbh.handle(callbacks);
+        }
+        catch(UnsupportedCallbackException e)
+        {
+            throw new SaslException("Handler does not support" +
+                                          " necessary callbacks",e);
+        }
+        catch(IOException e)
+        {
+            throw new SaslException("IO exception in CallbackHandler.", e);
+        }
+
+        if (realmSize > 1)
+        {
+            int[] selections =
+             ((RealmChoiceCallback)callbacks[0]).getSelectedIndexes();
+
+            if (selections.length > 0)
+                m_realm =
+                ((RealmChoiceCallback)callbacks[0]).getChoices()[selections[0]];
+            else
+                m_realm = ((RealmChoiceCallback)callbacks[0]).getChoices()[0];
+        }
+        else
+            m_realm = ((RealmCallback)callbacks[0]).getText();
+
+        m_clientNonce = getClientNonce();
+
+        m_name = ((NameCallback)callbacks[2]).getName();
+        if (m_name == null)
+            m_name = ((NameCallback)callbacks[2]).getDefaultName();
+        if (m_name == null)
+            throw new SaslException("No user name was specified.");
+
+        m_HA1 = DigestCalcHA1(
+                      m_dc.getAlgorithm(),
+                      m_name,
+                      m_realm,
+                      new String(((PasswordCallback)callbacks[1]).getPassword()),
+                      m_dc.getNonce(),
+                      m_clientNonce);
+
+        response = DigestCalcResponse(m_HA1,
+                                      m_dc.getNonce(),
+                                      "00000001",
+                                      m_clientNonce,
+                                      m_qopValue,
+                                      "AUTHENTICATE",
+                                      m_digestURI,
+                                      true);
+
+        digestResponse.append("username=\"");
+        digestResponse.append(m_authorizationId);
+        if (0 != m_realm.length())
+        {
+            digestResponse.append("\",realm=\"");
+            digestResponse.append(m_realm);
+        }
+        digestResponse.append("\",cnonce=\"");
+        digestResponse.append(m_clientNonce);
+        digestResponse.append("\",nc=");
+        digestResponse.append("00000001"); //nounce count
+        digestResponse.append(",qop=");
+        digestResponse.append(m_qopValue);
+        digestResponse.append(",digest-uri=\"");
+	digestResponse.append(m_digestURI);
+        digestResponse.append("\",response=");
+        digestResponse.append(response);
+        digestResponse.append(",charset=utf-8,nonce=\"");
+        digestResponse.append(m_dc.getNonce());
+        digestResponse.append("\"");
+
+        return digestResponse.toString();
+     }
+     
+     
+    /**
+     * This function validates the server response. This step performs a 
+     * modicum of mutual authentication by verifying that the server knows
+     * the user's password
+     *
+     * @param  serverResponse  Response recived form Server
+     *
+     * @return  true if the mutual authentication succeeds;
+     *          else return false
+     *
+     * @exception SaslException  If an error occurs
+     */
+    boolean checkServerResponseAuth(
+            byte[]  serverResponse) throws SaslException
+    {
+        char[]           response;
+        ResponseAuth  responseAuth = null;
+        String        responseStr;
+
+        responseAuth = new ResponseAuth(serverResponse);
+
+        response = DigestCalcResponse(m_HA1,
+                                  m_dc.getNonce(),
+                                  "00000001",
+                                  m_clientNonce,
+                                  m_qopValue,
+                                  DIGEST_METHOD,
+                                  m_digestURI,
+                                  false);
+
+        responseStr = new String(response);
+
+        return responseStr.equals(responseAuth.getResponseValue());
+    }
+
+
+    /**
+     * This function returns hex character representing the value of the input
+     * 
+     * @param value Input value in byte
+     *
+     * @return Hex value of the Input byte value
+     */
+    private static char getHexChar(
+        byte    value)
+    {
+        switch (value)
+        {
+        case 0:
+            return '0';
+        case 1:
+            return '1';
+        case 2:
+            return '2';
+        case 3:
+            return '3';
+        case 4:
+            return '4';
+        case 5:
+            return '5';
+        case 6:
+            return '6';
+        case 7:
+            return '7';
+        case 8:
+            return '8';
+        case 9:
+            return '9';
+        case 10:
+            return 'a';
+        case 11:
+            return 'b';
+        case 12:
+            return 'c';
+        case 13:
+            return 'd';
+        case 14:
+            return 'e';
+        case 15:
+            return 'f';
+        default:
+            return 'Z';
+        }
+    }
+
+    /**
+     * Calculates the Nonce value of the Client
+     * 
+     * @return   Nonce value of the client
+     *
+     * @exception   SaslException If an error Occurs
+     */
+    String getClientNonce() throws SaslException
+    {
+        byte[]          nonceBytes = new byte[NONCE_BYTE_COUNT];
+        SecureRandom    prng;
+        byte            nonceByte;
+        char[]          hexNonce = new char[NONCE_HEX_COUNT];
+
+        try
+        {
+            prng = SecureRandom.getInstance("SHA1PRNG");
+            prng.nextBytes(nonceBytes);
+            for(int i=0; i<NONCE_BYTE_COUNT; i++)
+            {
+                //low nibble
+                hexNonce[i*2] = getHexChar((byte)(nonceBytes[i] & 0x0f));
+                //high nibble
+                hexNonce[(i*2)+1] = getHexChar((byte)((nonceBytes[i] & 0xf0)
+                                                                      >> 4));
+            }
+            return new String(hexNonce);
+        }
+        catch(NoSuchAlgorithmException e)
+        {
+            throw new SaslException("No random number generator available", e);
+        }
+    }
+
+    /**
+     * Returns the IANA-registered mechanism name of this SASL client.
+     *  (e.g. "CRAM-MD5", "GSSAPI")
+     *
+     * @return  "DIGEST-MD5"the IANA-registered mechanism name of this SASL
+     *          client.
+     */
+    public String getMechanismName()
+    {
+        return "DIGEST-MD5";
+    }
+
+} //end class DigestMD5SaslClient
+
diff --git a/src/com/novell/sasl/client/DirectiveList.java b/src/com/novell/sasl/client/DirectiveList.java
new file mode 100644
index 0000000..fc26a6b
--- /dev/null
+++ b/src/com/novell/sasl/client/DirectiveList.java
@@ -0,0 +1,363 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/DirectiveList.java,v 1.4 2005/01/17 15:00:54 sunilk Exp $
+ *
+ * Copyright (C) 2002 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+import java.util.*;
+import org.apache.harmony.javax.security.sasl.*;
+import java.io.UnsupportedEncodingException;
+
+/**
+ * Implements the DirectiveList class whihc will be used by the 
+ * DigestMD5SaslClient class
+ */
+class DirectiveList extends Object
+{
+    private static final int STATE_LOOKING_FOR_FIRST_DIRECTIVE  = 1;
+    private static final int STATE_LOOKING_FOR_DIRECTIVE        = 2;
+    private static final int STATE_SCANNING_NAME                = 3;
+    private static final int STATE_LOOKING_FOR_EQUALS            = 4;
+    private static final int STATE_LOOKING_FOR_VALUE            = 5;
+    private static final int STATE_LOOKING_FOR_COMMA            = 6;
+    private static final int STATE_SCANNING_QUOTED_STRING_VALUE    = 7;
+    private static final int STATE_SCANNING_TOKEN_VALUE            = 8;
+    private static final int STATE_NO_UTF8_SUPPORT              = 9;
+
+    private int        m_curPos;
+    private int        m_errorPos;
+    private String     m_directives;
+    private int        m_state;
+    private ArrayList  m_directiveList;
+    private String     m_curName;
+    private int        m_scanStart;
+
+    /**
+     *  Constructs a new DirectiveList.
+     */
+     DirectiveList(
+        byte[] directives)
+    {
+        m_curPos = 0;
+        m_state = STATE_LOOKING_FOR_FIRST_DIRECTIVE;
+        m_directiveList = new ArrayList(10);
+        m_scanStart = 0;
+        m_errorPos = -1;
+        try
+        {
+            m_directives = new String(directives, "UTF-8");
+        }
+        catch(UnsupportedEncodingException e)
+        {
+            m_state = STATE_NO_UTF8_SUPPORT;
+        }
+    }
+
+    /**
+     * This function takes a US-ASCII character string containing a list of comma
+     * separated directives, and parses the string into the individual directives
+     * and their values. A directive consists of a token specifying the directive
+     * name followed by an equal sign (=) and the directive value. The value is
+     * either a token or a quoted string
+     *
+     * @exception SaslException  If an error Occurs
+     */
+    void parseDirectives() throws SaslException
+    {
+        char        prevChar;
+        char        currChar;
+        int            rc = 0;
+        boolean        haveQuotedPair = false;
+        String      currentName = "<no name>";
+
+        if (m_state == STATE_NO_UTF8_SUPPORT)
+            throw new SaslException("No UTF-8 support on platform");
+
+        prevChar = 0;
+
+        while (m_curPos < m_directives.length())
+        {
+            currChar = m_directives.charAt(m_curPos);
+            switch (m_state)
+            {
+            case STATE_LOOKING_FOR_FIRST_DIRECTIVE:
+            case STATE_LOOKING_FOR_DIRECTIVE:
+                if (isWhiteSpace(currChar))
+                {
+                    break;
+                }
+                else if (isValidTokenChar(currChar))
+                {
+                    m_scanStart = m_curPos;
+                    m_state = STATE_SCANNING_NAME;
+                }
+                else
+                {
+                     m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Invalid name character");
+                }
+                break;
+
+            case STATE_SCANNING_NAME:
+                if (isValidTokenChar(currChar))
+                {
+                    break;
+                }
+                else if (isWhiteSpace(currChar))
+                {
+                    currentName = m_directives.substring(m_scanStart, m_curPos);
+                    m_state = STATE_LOOKING_FOR_EQUALS;
+                }
+                else if ('=' == currChar)
+                {
+                    currentName = m_directives.substring(m_scanStart, m_curPos);
+                    m_state = STATE_LOOKING_FOR_VALUE;
+                }
+                else
+                {
+                     m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Invalid name character");
+                }
+                break;
+
+            case STATE_LOOKING_FOR_EQUALS:
+                if (isWhiteSpace(currChar))
+                {
+                    break;
+                }
+                else if ('=' == currChar)
+                {
+                    m_state = STATE_LOOKING_FOR_VALUE;
+                }
+                else
+                {
+                    m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Expected equals sign '='.");
+                }
+                break;
+
+            case STATE_LOOKING_FOR_VALUE:
+                if (isWhiteSpace(currChar))
+                {
+                    break;
+                }
+                else if ('"' == currChar)
+                {
+                    m_scanStart = m_curPos+1; /* don't include the quote */
+                    m_state = STATE_SCANNING_QUOTED_STRING_VALUE;
+                }
+                else if (isValidTokenChar(currChar))
+                {
+                    m_scanStart = m_curPos;
+                    m_state = STATE_SCANNING_TOKEN_VALUE;
+                }
+                else
+                {
+                    m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Unexpected character");
+                }
+                break;
+
+            case STATE_SCANNING_TOKEN_VALUE:
+                if (isValidTokenChar(currChar))
+                {
+                    break;
+                }
+                else if (isWhiteSpace(currChar))
+                {
+                    addDirective(currentName, false);
+                    m_state = STATE_LOOKING_FOR_COMMA;
+                }
+                else if (',' == currChar)
+                {
+                    addDirective(currentName, false);
+                    m_state = STATE_LOOKING_FOR_DIRECTIVE;
+                }
+                else
+                {
+                     m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Invalid value character");
+                }
+                break;
+
+            case STATE_SCANNING_QUOTED_STRING_VALUE:
+                if ('\\' == currChar)
+                    haveQuotedPair = true;
+                if ( ('"' == currChar) &&
+                     ('\\' != prevChar) )
+                {
+                    addDirective(currentName, haveQuotedPair);
+                    haveQuotedPair = false;
+                    m_state = STATE_LOOKING_FOR_COMMA;
+                }
+                break;
+
+            case STATE_LOOKING_FOR_COMMA:
+                if (isWhiteSpace(currChar))
+                    break;
+                else if (currChar == ',')
+                    m_state = STATE_LOOKING_FOR_DIRECTIVE;
+                else
+                {
+                    m_errorPos = m_curPos;
+                    throw new SaslException("Parse error: Expected a comma.");
+                }
+                break;
+            }
+            if (0 != rc)
+                break;
+            prevChar = currChar;
+            m_curPos++;
+        } /* end while loop */
+
+
+        if (rc == 0)
+        {
+            /* check the ending state */
+            switch (m_state)
+            {
+            case STATE_SCANNING_TOKEN_VALUE:
+                addDirective(currentName, false);
+                break;
+
+            case STATE_LOOKING_FOR_FIRST_DIRECTIVE:
+            case STATE_LOOKING_FOR_COMMA:
+                break;
+
+            case STATE_LOOKING_FOR_DIRECTIVE:
+                    throw new SaslException("Parse error: Trailing comma.");
+
+            case STATE_SCANNING_NAME:
+            case STATE_LOOKING_FOR_EQUALS:
+            case STATE_LOOKING_FOR_VALUE:
+                    throw new SaslException("Parse error: Missing value.");
+
+            case STATE_SCANNING_QUOTED_STRING_VALUE:
+                    throw new SaslException("Parse error: Missing closing quote.");
+            }
+        }
+
+    }
+
+    /**
+     * This function returns TRUE if the character is a valid token character.
+     *
+     *     token          = 1*<any CHAR except CTLs or separators>
+     *
+     *      separators     = "(" | ")" | "<" | ">" | "@"
+     *                     | "," | ";" | ":" | "\" | <">
+     *                     | "/" | "[" | "]" | "?" | "="
+     *                     | "{" | "}" | SP | HT
+     *
+     *      CTL            = <any US-ASCII control character
+     *                       (octets 0 - 31) and DEL (127)>
+     *
+     *      CHAR           = <any US-ASCII character (octets 0 - 127)>
+     *
+     * @param c  character to be tested
+     *
+     * @return Returns TRUE if the character is a valid token character.
+     */
+    boolean isValidTokenChar(
+        char c)
+    {
+        if ( ( (c >= '\u0000') && (c <='\u0020') ) ||
+             ( (c >= '\u003a') && (c <= '\u0040') ) ||
+             ( (c >= '\u005b') && (c <= '\u005d') ) ||
+             ('\u002c' == c) ||
+             ('\u0025' == c) ||
+             ('\u0028' == c) ||
+             ('\u0029' == c) ||
+             ('\u007b' == c) ||
+             ('\u007d' == c) ||
+             ('\u007f' == c) )
+            return false;
+
+        return true;
+    }
+
+    /**
+     * This function returns TRUE if the character is linear white space (LWS).
+     *         LWS = [CRLF] 1*( SP | HT )
+     * @param c  Input charcter to be tested
+     *
+     * @return Returns TRUE if the character is linear white space (LWS)
+     */
+    boolean isWhiteSpace(
+        char c)
+    {
+        if ( ('\t' == c) ||  // HORIZONTAL TABULATION.
+             ('\n' == c) ||  // LINE FEED.
+             ('\r' == c) ||  // CARRIAGE RETURN.
+             ('\u0020' == c) )
+            return true;
+
+        return false;
+    }
+
+    /**
+     * This function creates a directive record and adds it to the list, the
+     * value will be added later after it is parsed.
+     *
+     * @param name  Name
+     * @param haveQuotedPair true if quoted pair is there else false
+     */
+    void addDirective(
+        String    name,
+        boolean   haveQuotedPair)
+    {
+        String value;
+        int    inputIndex;
+        int    valueIndex;
+        char   valueChar;
+        int    type;
+
+        if (!haveQuotedPair)
+        {
+            value = m_directives.substring(m_scanStart, m_curPos);
+        }
+        else
+        { //copy one character at a time skipping backslash excapes.
+            StringBuffer valueBuf = new StringBuffer(m_curPos - m_scanStart);
+            valueIndex = 0;
+            inputIndex = m_scanStart;
+            while (inputIndex < m_curPos)
+            {
+                if ('\\' == (valueChar = m_directives.charAt(inputIndex)))
+                    inputIndex++;
+                valueBuf.setCharAt(valueIndex, m_directives.charAt(inputIndex));
+                valueIndex++;
+                inputIndex++;
+            }
+            value = new String(valueBuf);
+        }
+
+        if (m_state == STATE_SCANNING_QUOTED_STRING_VALUE)
+            type = ParsedDirective.QUOTED_STRING_VALUE;
+        else
+            type = ParsedDirective.TOKEN_VALUE;
+        m_directiveList.add(new ParsedDirective(name, value, type));
+    }
+
+
+    /**
+     * Returns the List iterator.
+     *
+     * @return     Returns the Iterator Object for the List.
+     */
+    Iterator getIterator()
+    {
+        return m_directiveList.iterator();
+    }
+}
+
diff --git a/src/com/novell/sasl/client/ParsedDirective.java b/src/com/novell/sasl/client/ParsedDirective.java
new file mode 100644
index 0000000..17bf70e
--- /dev/null
+++ b/src/com/novell/sasl/client/ParsedDirective.java
@@ -0,0 +1,56 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/ParsedDirective.java,v 1.1 2003/08/21 10:06:26 kkanil Exp $
+ *
+ * Copyright (C) 2002 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+/**
+ * Implements the ParsedDirective class which will be used in the
+ * DigestMD5SaslClient mechanism.
+ */
+class ParsedDirective
+{
+    public static final int  QUOTED_STRING_VALUE = 1;
+    public static final int  TOKEN_VALUE         = 2;
+
+    private int     m_valueType;
+    private String  m_name;
+    private String  m_value;
+
+    ParsedDirective(
+        String  name,
+        String  value,
+        int     type)
+    {
+        m_name = name;
+        m_value = value;
+        m_valueType = type;
+    }
+
+    String getValue()
+    {
+        return m_value;
+    }
+
+    String getName()
+    {
+        return m_name;
+    }
+
+    int getValueType()
+    {
+        return m_valueType;
+    }
+
+}
+
diff --git a/src/com/novell/sasl/client/ResponseAuth.java b/src/com/novell/sasl/client/ResponseAuth.java
new file mode 100644
index 0000000..0aef955
--- /dev/null
+++ b/src/com/novell/sasl/client/ResponseAuth.java
@@ -0,0 +1,83 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/ResponseAuth.java,v 1.3 2005/01/17 15:00:54 sunilk Exp $
+ *
+ * Copyright (C) 2002 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+import java.util.*;
+import org.apache.harmony.javax.security.sasl.*;
+
+/**
+ * Implements the ResponseAuth class used by the DigestMD5SaslClient mechanism
+ */
+class ResponseAuth
+{
+
+    private String m_responseValue;
+
+    ResponseAuth(
+        byte[] responseAuth)
+            throws SaslException
+    {
+        m_responseValue = null;
+
+        DirectiveList dirList = new DirectiveList(responseAuth);
+        try
+        {
+            dirList.parseDirectives();
+            checkSemantics(dirList);
+        }
+        catch (SaslException e)
+        {
+        }
+    }
+
+    /**
+     * Checks the semantics of the directives in the directive list as parsed
+     * from the digest challenge byte array.
+     *
+     * @param dirList  the list of directives parsed from the digest challenge
+     *
+     * @exception SaslException   If a semantic error occurs
+     */
+    void checkSemantics(
+        DirectiveList dirList) throws SaslException
+    {
+        Iterator        directives = dirList.getIterator();
+        ParsedDirective directive;
+        String          name;
+
+        while (directives.hasNext())
+        {
+            directive = (ParsedDirective)directives.next();
+            name = directive.getName();
+            if (name.equals("rspauth"))
+                m_responseValue = directive.getValue();
+        }
+
+        /* post semantic check */
+        if (m_responseValue == null)
+            throw new SaslException("Missing response-auth directive.");
+    }
+
+    /**
+     * returns the ResponseValue
+     *
+     * @return the ResponseValue as a String.
+     */
+    public String getResponseValue()
+    {
+        return m_responseValue;
+    }
+}
+
diff --git a/src/com/novell/sasl/client/TokenParser.java b/src/com/novell/sasl/client/TokenParser.java
new file mode 100644
index 0000000..3d3491d
--- /dev/null
+++ b/src/com/novell/sasl/client/TokenParser.java
@@ -0,0 +1,208 @@
+/* **************************************************************************
+ * $OpenLDAP: /com/novell/sasl/client/TokenParser.java,v 1.3 2005/01/17 15:00:54 sunilk Exp $
+ *
+ * Copyright (C) 2002 Novell, Inc. All Rights Reserved.
+ *
+ * THIS WORK IS SUBJECT TO U.S. AND INTERNATIONAL COPYRIGHT LAWS AND
+ * TREATIES. USE, MODIFICATION, AND REDISTRIBUTION OF THIS WORK IS SUBJECT
+ * TO VERSION 2.0.1 OF THE OPENLDAP PUBLIC LICENSE, A COPY OF WHICH IS
+ * AVAILABLE AT HTTP://WWW.OPENLDAP.ORG/LICENSE.HTML OR IN THE FILE "LICENSE"
+ * IN THE TOP-LEVEL DIRECTORY OF THE DISTRIBUTION. ANY USE OR EXPLOITATION
+ * OF THIS WORK OTHER THAN AS AUTHORIZED IN VERSION 2.0.1 OF THE OPENLDAP
+ * PUBLIC LICENSE, OR OTHER PRIOR WRITTEN CONSENT FROM NOVELL, COULD SUBJECT
+ * THE PERPETRATOR TO CRIMINAL AND CIVIL LIABILITY.
+ ******************************************************************************/
+package com.novell.sasl.client;
+
+import org.apache.harmony.javax.security.sasl.*;
+/**
+ * The TokenParser class will parse individual tokens from a list of tokens that
+ * are a directive value for a DigestMD5 authentication.The tokens are separated
+ * commas.
+ */
+class TokenParser extends Object
+{
+    private static final int STATE_LOOKING_FOR_FIRST_TOKEN = 1;
+    private static final int STATE_LOOKING_FOR_TOKEN       = 2;
+    private static final int STATE_SCANNING_TOKEN          = 3;
+    private static final int STATE_LOOKING_FOR_COMMA       = 4;
+    private static final int STATE_PARSING_ERROR           = 5;
+    private static final int STATE_DONE                    = 6;
+
+    private int        m_curPos;
+    private int     m_scanStart;
+    private int     m_state;
+    private String  m_tokens;
+
+
+    TokenParser(
+        String tokens)
+    {
+        m_tokens = tokens;
+        m_curPos = 0;
+        m_scanStart = 0;
+        m_state =  STATE_LOOKING_FOR_FIRST_TOKEN;
+    }
+
+    /**
+     * This function parses the next token from the tokens string and returns
+     * it as a string. If there are no more tokens a null reference is returned.
+     *
+     * @return  the parsed token or a null reference if there are no more
+     * tokens
+     *
+     * @exception  SASLException if an error occurs while parsing
+     */
+    String parseToken() throws SaslException
+    {
+        char    currChar;
+        String  token = null;
+
+
+        if (m_state == STATE_DONE)
+            return null;
+
+        while (m_curPos < m_tokens.length() && (token == null))
+        {
+            currChar = m_tokens.charAt(m_curPos);
+            switch (m_state)
+            {
+            case STATE_LOOKING_FOR_FIRST_TOKEN:
+            case STATE_LOOKING_FOR_TOKEN:
+                if (isWhiteSpace(currChar))
+                {
+                    break;
+                }
+                else if (isValidTokenChar(currChar))
+                {
+                    m_scanStart = m_curPos;
+                    m_state = STATE_SCANNING_TOKEN;
+                }
+                else
+                {
+                    m_state = STATE_PARSING_ERROR;
+                    throw new SaslException("Invalid token character at position " + m_curPos);
+                }
+                break;
+
+            case STATE_SCANNING_TOKEN:
+                if (isValidTokenChar(currChar))
+                {
+                    break;
+                }
+                else if (isWhiteSpace(currChar))
+                {
+                    token = m_tokens.substring(m_scanStart, m_curPos);
+                    m_state = STATE_LOOKING_FOR_COMMA;
+                }
+                else if (',' == currChar)
+                {
+                    token = m_tokens.substring(m_scanStart, m_curPos);
+                    m_state = STATE_LOOKING_FOR_TOKEN;
+                }
+                else
+                {
+                    m_state = STATE_PARSING_ERROR;
+                    throw new SaslException("Invalid token character at position " + m_curPos);
+                }
+                break;
+
+
+            case STATE_LOOKING_FOR_COMMA:
+                if (isWhiteSpace(currChar))
+                    break;
+                else if (currChar == ',')
+                    m_state = STATE_LOOKING_FOR_TOKEN;
+                else
+                {
+                    m_state = STATE_PARSING_ERROR;
+                    throw new SaslException("Expected a comma, found '" +
+                                            currChar + "' at postion " +
+                                            m_curPos);
+                }
+                break;
+            }
+            m_curPos++;
+        } /* end while loop */
+
+        if (token == null)
+        {    /* check the ending state */
+            switch (m_state)
+            {
+            case STATE_SCANNING_TOKEN:
+                token = m_tokens.substring(m_scanStart);
+                m_state = STATE_DONE;
+                break;
+
+            case STATE_LOOKING_FOR_FIRST_TOKEN:
+            case STATE_LOOKING_FOR_COMMA:
+                break;
+
+            case STATE_LOOKING_FOR_TOKEN:
+                throw new SaslException("Trialing comma");
+            }
+        }
+
+        return token;
+    }
+
+    /**
+     * This function returns TRUE if the character is a valid token character.
+     *
+     *     token          = 1*<any CHAR except CTLs or separators>
+     *
+     *      separators     = "(" | ")" | "<" | ">" | "@"
+     *                     | "," | ";" | ":" | "\" | <">
+     *                     | "/" | "[" | "]" | "?" | "="
+     *                     | "{" | "}" | SP | HT
+     *
+     *      CTL            = <any US-ASCII control character
+     *                       (octets 0 - 31) and DEL (127)>
+     *
+     *      CHAR           = <any US-ASCII character (octets 0 - 127)>
+     *
+     * @param c  character to be validated
+     *
+     * @return True if character is valid Token character else it returns 
+     * false
+     */
+    boolean isValidTokenChar(
+        char c)
+    {
+        if ( ( (c >= '\u0000') && (c <='\u0020') ) ||
+             ( (c >= '\u003a') && (c <= '\u0040') ) ||
+             ( (c >= '\u005b') && (c <= '\u005d') ) ||
+             ('\u002c' == c) ||
+             ('\u0025' == c) ||
+             ('\u0028' == c) ||
+             ('\u0029' == c) ||
+             ('\u007b' == c) ||
+             ('\u007d' == c) ||
+             ('\u007f' == c) )
+            return false;
+
+        return true;
+    }
+
+    /**
+     * This function returns TRUE if the character is linear white space (LWS).
+     *         LWS = [CRLF] 1*( SP | HT )
+     *
+     * @param c  character to be validated
+     *
+     * @return True if character is liner whitespace else it returns false
+     */
+    boolean isWhiteSpace(
+        char c)
+    {
+        if ( ('\t' == c) || // HORIZONTAL TABULATION.
+             ('\n' == c) || // LINE FEED.
+             ('\r' == c) || // CARRIAGE RETURN.
+             ('\u0020' == c) )
+            return true;
+
+        return false;
+    }
+
+}
+
diff --git a/src/de/measite/smack/AndroidDebugger.java b/src/de/measite/smack/AndroidDebugger.java
new file mode 100644
index 0000000..4dfc622
--- /dev/null
+++ b/src/de/measite/smack/AndroidDebugger.java
@@ -0,0 +1,185 @@
+package de.measite.smack;
+
+import org.jivesoftware.smack.debugger.SmackDebugger;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.*;
+
+import android.util.Log;
+
+import java.io.Reader;
+import java.io.Writer;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * Very simple debugger that prints to the android log the sent and received stanzas. Use
+ * this debugger with caution since printing to the console is an expensive operation that may
+ * even block the thread since only one thread may print at a time.<p>
+ * <p/>
+ * It is possible to not only print the raw sent and received stanzas but also the interpreted
+ * packets by Smack. By default interpreted packets won't be printed. To enable this feature
+ * just change the <tt>printInterpreted</tt> static variable to <tt>true</tt>.
+ *
+ * @author Gaston Dombiak
+ */
+public class AndroidDebugger implements SmackDebugger {
+
+    public static boolean printInterpreted = false;
+    private SimpleDateFormat dateFormatter = new SimpleDateFormat("hh:mm:ss aaa");
+
+    private Connection connection = null;
+
+    private PacketListener listener = null;
+    private ConnectionListener connListener = null;
+
+    private Writer writer;
+    private Reader reader;
+    private ReaderListener readerListener;
+    private WriterListener writerListener;
+
+    public AndroidDebugger(Connection connection, Writer writer, Reader reader) {
+        this.connection = connection;
+        this.writer = writer;
+        this.reader = reader;
+        createDebug();
+    }
+
+    /**
+     * Creates the listeners that will print in the console when new activity is detected.
+     */
+    private void createDebug() {
+        // Create a special Reader that wraps the main Reader and logs data to the GUI.
+        ObservableReader debugReader = new ObservableReader(reader);
+        readerListener = new ReaderListener() {
+            public void read(String str) {
+            	Log.d("SMACK",
+                        dateFormatter.format(new Date()) + " RCV  (" + connection.hashCode() +
+                        "): " +
+                        str);
+            }
+        };
+        debugReader.addReaderListener(readerListener);
+
+        // Create a special Writer that wraps the main Writer and logs data to the GUI.
+        ObservableWriter debugWriter = new ObservableWriter(writer);
+        writerListener = new WriterListener() {
+            public void write(String str) {
+            	Log.d("SMACK",
+                        dateFormatter.format(new Date()) + " SENT (" + connection.hashCode() +
+                        "): " +
+                        str);
+            }
+        };
+        debugWriter.addWriterListener(writerListener);
+
+        // Assign the reader/writer objects to use the debug versions. The packet reader
+        // and writer will use the debug versions when they are created.
+        reader = debugReader;
+        writer = debugWriter;
+
+        // Create a thread that will listen for all incoming packets and write them to
+        // the GUI. This is what we call "interpreted" packet data, since it's the packet
+        // data as Smack sees it and not as it's coming in as raw XML.
+        listener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                if (printInterpreted) {
+                	Log.d("SMACK",
+                            dateFormatter.format(new Date()) + " RCV PKT (" +
+                            connection.hashCode() +
+                            "): " +
+                            packet.toXML());
+                }
+            }
+        };
+
+        connListener = new ConnectionListener() {
+            public void connectionClosed() {
+                Log.d("SMACK",
+                        dateFormatter.format(new Date()) + " Connection closed (" +
+                        connection.hashCode() +
+                        ")");
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                Log.d("SMACK",
+                        dateFormatter.format(new Date()) +
+                        " Connection closed due to an exception (" +
+                        connection.hashCode() +
+                        ")");
+                e.printStackTrace();
+            }
+            public void reconnectionFailed(Exception e) {
+                Log.d("SMACK",
+                        dateFormatter.format(new Date()) +
+                        " Reconnection failed due to an exception (" +
+                        connection.hashCode() +
+                        ")");
+                e.printStackTrace();
+            }
+            public void reconnectionSuccessful() {
+                Log.d("SMACK",
+                        dateFormatter.format(new Date()) + " Connection reconnected (" +
+                        connection.hashCode() +
+                        ")");
+            }
+            public void reconnectingIn(int seconds) {
+                Log.d("SMACK",
+                        dateFormatter.format(new Date()) + " Connection (" +
+                        connection.hashCode() +
+                        ") will reconnect in " + seconds);
+            }
+        };
+    }
+
+    public Reader newConnectionReader(Reader newReader) {
+        ((ObservableReader)reader).removeReaderListener(readerListener);
+        ObservableReader debugReader = new ObservableReader(newReader);
+        debugReader.addReaderListener(readerListener);
+        reader = debugReader;
+        return reader;
+    }
+
+    public Writer newConnectionWriter(Writer newWriter) {
+        ((ObservableWriter)writer).removeWriterListener(writerListener);
+        ObservableWriter debugWriter = new ObservableWriter(newWriter);
+        debugWriter.addWriterListener(writerListener);
+        writer = debugWriter;
+        return writer;
+    }
+
+    public void userHasLogged(String user) {
+        boolean isAnonymous = "".equals(StringUtils.parseName(user));
+        String title =
+                "User logged (" + connection.hashCode() + "): "
+                + (isAnonymous ? "" : StringUtils.parseBareAddress(user))
+                + "@"
+                + connection.getServiceName()
+                + ":"
+                + connection.getPort();
+        title += "/" + StringUtils.parseResource(user);
+        Log.d("SMACK", title);
+        // Add the connection listener to the connection so that the debugger can be notified
+        // whenever the connection is closed.
+        connection.addConnectionListener(connListener);
+    }
+
+    public Reader getReader() {
+        return reader;
+    }
+
+    public Writer getWriter() {
+        return writer;
+    }
+
+    public PacketListener getReaderListener() {
+        return listener;
+    }
+
+    public PacketListener getWriterListener() {
+        return null;
+    }
+}
+
diff --git a/src/de/measite/smack/Sasl.java b/src/de/measite/smack/Sasl.java
new file mode 100644
index 0000000..a59135d
--- /dev/null
+++ b/src/de/measite/smack/Sasl.java
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2009 Rene Treffer
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+package de.measite.smack;
+
+import java.util.Enumeration;
+import java.util.Hashtable;
+import java.util.Map;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslException;
+import org.apache.harmony.javax.security.sasl.SaslServer;
+import org.apache.harmony.javax.security.sasl.SaslServerFactory;
+
+public class Sasl {
+
+    // SaslClientFactory service name
+    private static final String CLIENTFACTORYSRV = "SaslClientFactory"; //$NON-NLS-1$
+
+    // SaslServerFactory service name
+    private static final String SERVERFACTORYSRV = "SaslServerFactory"; //$NON-NLS-1$
+
+    public static final String POLICY_NOPLAINTEXT = "javax.security.sasl.policy.noplaintext"; //$NON-NLS-1$
+
+    public static final String POLICY_NOACTIVE = "javax.security.sasl.policy.noactive"; //$NON-NLS-1$
+
+    public static final String POLICY_NODICTIONARY = "javax.security.sasl.policy.nodictionary"; //$NON-NLS-1$
+
+    public static final String POLICY_NOANONYMOUS = "javax.security.sasl.policy.noanonymous"; //$NON-NLS-1$
+
+    public static final String POLICY_FORWARD_SECRECY = "javax.security.sasl.policy.forward"; //$NON-NLS-1$
+
+    public static final String POLICY_PASS_CREDENTIALS = "javax.security.sasl.policy.credentials"; //$NON-NLS-1$
+
+    public static final String MAX_BUFFER = "javax.security.sasl.maxbuffer"; //$NON-NLS-1$
+
+    public static final String RAW_SEND_SIZE = "javax.security.sasl.rawsendsize"; //$NON-NLS-1$
+
+    public static final String REUSE = "javax.security.sasl.reuse"; //$NON-NLS-1$
+
+    public static final String QOP = "javax.security.sasl.qop"; //$NON-NLS-1$
+
+    public static final String STRENGTH = "javax.security.sasl.strength"; //$NON-NLS-1$
+
+    public static final String SERVER_AUTH = "javax.security.sasl.server.authentication"; //$NON-NLS-1$
+
+    public static Enumeration<SaslClientFactory> getSaslClientFactories() {
+        Hashtable<SaslClientFactory,Object> factories = new Hashtable<SaslClientFactory,Object>();
+        factories.put(new SaslClientFactory(), new Object());
+        return factories.keys();
+    }
+
+    public static Enumeration<SaslServerFactory> getSaslServerFactories() {
+        return org.apache.harmony.javax.security.sasl.Sasl.getSaslServerFactories();
+    }
+
+    public static SaslServer createSaslServer(String mechanism, String protocol,
+            String serverName, Map<String, ?> prop, CallbackHandler cbh) throws SaslException {
+        return org.apache.harmony.javax.security.sasl.Sasl.createSaslServer(mechanism, protocol, serverName, prop, cbh);
+    }
+
+    public static SaslClient createSaslClient(String[] mechanisms, String authanticationID,
+            String protocol, String serverName, Map<String, ?> prop, CallbackHandler cbh)
+            throws SaslException {
+        if (mechanisms == null) {
+            throw new NullPointerException("auth.33"); //$NON-NLS-1$
+        }
+        SaslClientFactory fact = getSaslClientFactories().nextElement();
+        String[] mech = fact.getMechanismNames(null);
+        boolean is = false;
+        if (mech != null) {
+            for (int j = 0; j < mech.length; j++) {
+                for (int n = 0; n < mechanisms.length; n++) {
+                    if (mech[j].equals(mechanisms[n])) {
+                        is = true;
+                        break;
+                    }
+                }
+            }
+        }
+        if (is) {
+            return fact.createSaslClient(
+                mechanisms,
+                authanticationID,
+                protocol,
+                serverName,
+                prop,
+                cbh
+            );
+        }
+        return null;
+    }
+
+}
diff --git a/src/de/measite/smack/SaslClientFactory.java b/src/de/measite/smack/SaslClientFactory.java
new file mode 100644
index 0000000..2fa1ebd
--- /dev/null
+++ b/src/de/measite/smack/SaslClientFactory.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright 2009 Rene Treffer
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+package de.measite.smack;
+
+import java.util.Map;
+
+import com.novell.sasl.client.DigestMD5SaslClient;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslException;
+import org.apache.qpid.management.common.sasl.PlainSaslClient;
+
+public class SaslClientFactory implements
+		org.apache.harmony.javax.security.sasl.SaslClientFactory {
+
+	@Override
+	public SaslClient createSaslClient(String[] mechanisms,
+			String authorizationId, String protocol, String serverName,
+			Map<String, ?> props, CallbackHandler cbh) throws SaslException {
+		for (String mech: mechanisms) {
+			if ("PLAIN".equals(mech)) {
+				return new PlainSaslClient(authorizationId, cbh);
+			} else
+			if ("DIGEST-MD5".equals(mech)) {
+				return DigestMD5SaslClient.getClient(
+					authorizationId,
+					protocol,
+					serverName,
+					props,
+					cbh
+				);
+			}
+		}
+		return null;
+	}
+
+	@Override
+	public String[] getMechanismNames(Map<String, ?> props) {
+		return new String[]{
+			"PLAIN",
+			"DIGEST-MD5"
+		};
+	}
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/AuthPermission.java b/src/org/apache/harmony/javax/security/auth/AuthPermission.java
new file mode 100644
index 0000000..bb12554
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/AuthPermission.java
@@ -0,0 +1,97 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+import java.security.BasicPermission;
+
+
+
+/**
+ * Governs the use of methods in this package and also its subpackages. A
+ * <i>target name</i> of the permission specifies which methods are allowed
+ * without specifying the concrete action lists. Possible target names and
+ * associated authentication permissions are:
+ *
+ * <pre>
+ *    doAs                      invoke Subject.doAs methods.
+ *    doAsPrivileged            invoke the Subject.doAsPrivileged methods.
+ *    getSubject                invoke Subject.getSubject().
+ *    getSubjectFromDomainCombiner    invoke SubjectDomainCombiner.getSubject().
+ *    setReadOnly               invoke Subject.setReadonly().
+ *    modifyPrincipals          modify the set of principals
+ *                              associated with a Subject.
+ *    modifyPublicCredentials   modify the set of public credentials
+ *                              associated with a Subject.
+ *    modifyPrivateCredentials  modify the set of private credentials
+ *                              associated with a Subject.
+ *    refreshCredential         invoke the refresh method on a credential of a
+ *                              refreshable credential class.
+ *    destroyCredential         invoke the destroy method on a credential of a
+ *                              destroyable credential class.
+ *    createLoginContext.<i>name</i>   instantiate a LoginContext with the
+ *                              specified name. The wildcard name ('*')
+ *                              allows to a LoginContext of any name.
+ *    getLoginConfiguration     invoke the getConfiguration method of
+ *                              javax.security.auth.login.Configuration.
+ *    refreshLoginConfiguration Invoke the refresh method of
+ *                              javax.security.auth.login.Configuration.
+ * </pre>
+ */
+public final class AuthPermission extends BasicPermission {
+
+    private static final long serialVersionUID = 5806031445061587174L;
+
+    private static final String CREATE_LOGIN_CONTEXT = "createLoginContext"; //$NON-NLS-1$
+
+    private static final String CREATE_LOGIN_CONTEXT_ANY = "createLoginContext.*"; //$NON-NLS-1$
+
+    // inits permission name.
+    private static String init(String name) {
+
+        if (name == null) {
+            throw new NullPointerException("auth.13"); //$NON-NLS-1$
+        }
+
+        if (CREATE_LOGIN_CONTEXT.equals(name)) {
+            return CREATE_LOGIN_CONTEXT_ANY;
+        }
+        return name;
+    }
+
+    /**
+     * Creates an authentication permission with the specified target name.
+     *
+     * @param name
+     *            the target name of this authentication permission.
+     */
+    public AuthPermission(String name) {
+        super(init(name));
+    }
+
+    /**
+     * Creates an authentication permission with the specified target name.
+     *
+     * @param name
+     *            the target name of this authentication permission.
+     * @param actions
+     *            this parameter is ignored and should be {@code null}.
+     */
+    public AuthPermission(String name, String actions) {
+        super(init(name), actions);
+    }
+}
\ No newline at end of file
diff --git a/src/org/apache/harmony/javax/security/auth/DestroyFailedException.java b/src/org/apache/harmony/javax/security/auth/DestroyFailedException.java
new file mode 100644
index 0000000..7c7ea79
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/DestroyFailedException.java
@@ -0,0 +1,44 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+/**
+ * Signals that the {@link Destroyable#destroy()} method failed.
+ */
+public class DestroyFailedException extends Exception {
+
+    private static final long serialVersionUID = -7790152857282749162L;
+
+    /**
+     * Creates an exception of type {@code DestroyFailedException}.
+     */
+    public DestroyFailedException() {
+        super();
+    }
+
+    /**
+     * Creates an exception of type {@code DestroyFailedException}.
+     *
+     * @param message
+     *            A detail message that describes the reason for this exception.
+     */
+    public DestroyFailedException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/Destroyable.java b/src/org/apache/harmony/javax/security/auth/Destroyable.java
new file mode 100644
index 0000000..12a107b
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/Destroyable.java
@@ -0,0 +1,43 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+/**
+ * Allows for special treatment of sensitive information, when it comes to
+ * destroying or clearing of the data.
+ */
+public interface Destroyable {
+
+    /**
+     * Erases the sensitive information. Once an object is destroyed any calls
+     * to its methods will throw an {@code IllegalStateException}. If it does
+     * not succeed a DestroyFailedException is thrown.
+     *
+     * @throws DestroyFailedException
+     *             if the information cannot be erased.
+     */
+    void destroy() throws DestroyFailedException;
+
+    /**
+     * Returns {@code true} once an object has been safely destroyed.
+     *
+     * @return whether the object has been safely destroyed.
+     */
+    boolean isDestroyed();
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/PrivateCredentialPermission.java b/src/org/apache/harmony/javax/security/auth/PrivateCredentialPermission.java
new file mode 100644
index 0000000..d62bb24
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/PrivateCredentialPermission.java
@@ -0,0 +1,395 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.Serializable;
+import java.security.Permission;
+import java.security.PermissionCollection;
+import java.security.Principal;
+import java.util.Set;
+
+
+
+/**
+ * Protects private credential objects belonging to a {@code Subject}. It has
+ * only one action which is "read". The target name of this permission has a
+ * special syntax:
+ *
+ * <pre>
+ * targetName = CredentialClass {PrincipalClass &quot;PrincipalName&quot;}*
+ * </pre>
+ *
+ * First it states a credential class and is followed then by a list of one or
+ * more principals identifying the subject.
+ * <p>
+ * The principals on their part are specified as the name of the {@code
+ * Principal} class followed by the principal name in quotes. For example, the
+ * following file may define permission to read the private credentials of a
+ * principal named "Bob": "com.sun.PrivateCredential com.sun.Principal \"Bob\""
+ * <p>
+ * The syntax also allows the use of the wildcard "*" in place of {@code
+ * CredentialClass} or {@code PrincipalClass} and/or {@code PrincipalName}.
+ *
+ * @see Principal
+ */
+public final class PrivateCredentialPermission extends Permission {
+
+    private static final long serialVersionUID = 5284372143517237068L;
+
+    // allowed action
+    private static final String READ = "read"; //$NON-NLS-1$
+
+    private String credentialClass;
+
+    // current offset        
+    private transient int offset;
+
+    // owners set
+    private transient CredOwner[] set;
+    
+    /**
+     * Creates a new permission for private credentials specified by the target
+     * name {@code name} and an {@code action}. The action is always
+     * {@code "read"}.
+     *
+     * @param name
+     *            the target name of the permission.
+     * @param action
+     *            the action {@code "read"}.
+     */
+    public PrivateCredentialPermission(String name, String action) {
+        super(name);
+        if (READ.equalsIgnoreCase(action)) {
+            initTargetName(name);
+        } else {
+            throw new IllegalArgumentException("auth.11"); //$NON-NLS-1$
+        }
+    }
+
+    /**
+     * Creates a {@code PrivateCredentialPermission} from the {@code Credential}
+     * class and set of principals.
+     * 
+     * @param credentialClass
+     *            the credential class name.
+     * @param principals
+     *            the set of principals.
+     */
+    PrivateCredentialPermission(String credentialClass, Set<Principal> principals) {
+        super(credentialClass);
+        this.credentialClass = credentialClass;
+
+        set = new CredOwner[principals.size()];
+        for (Principal p : principals) {
+            CredOwner element = new CredOwner(p.getClass().getName(), p.getName());
+            // check for duplicate elements
+            boolean found = false;
+            for (int ii = 0; ii < offset; ii++) {
+                if (set[ii].equals(element)) {
+                    found = true;
+                    break;
+                }
+            }
+            if (!found) {
+                set[offset++] = element;
+            }
+        }
+    }
+
+    /**
+     * Initialize a PrivateCredentialPermission object and checks that a target
+     * name has a correct format: CredentialClass 1*(PrincipalClass
+     * "PrincipalName")
+     */
+    private void initTargetName(String name) {
+
+        if (name == null) {
+            throw new NullPointerException("auth.0E"); //$NON-NLS-1$
+        }
+
+        // check empty string
+        name = name.trim();
+        if (name.length() == 0) {
+            throw new IllegalArgumentException("auth.0F"); //$NON-NLS-1$
+        }
+
+        // get CredentialClass
+        int beg = name.indexOf(' ');
+        if (beg == -1) {
+            throw new IllegalArgumentException("auth.10"); //$NON-NLS-1$
+        }
+        credentialClass = name.substring(0, beg);
+
+        // get a number of pairs: PrincipalClass "PrincipalName"
+        beg++;
+        int count = 0;
+        int nameLength = name.length();
+        for (int i, j = 0; beg < nameLength; beg = j + 2, count++) {
+            i = name.indexOf(' ', beg);
+            j = name.indexOf('"', i + 2);
+
+            if (i == -1 || j == -1 || name.charAt(i + 1) != '"') {
+                throw new IllegalArgumentException("auth.10"); //$NON-NLS-1$
+            }
+        }
+
+        // name MUST have one pair at least
+        if (count < 1) {
+            throw new IllegalArgumentException("auth.10"); //$NON-NLS-1$
+        }
+
+        beg = name.indexOf(' ');
+        beg++;
+
+        // populate principal set with instances of CredOwner class
+        String principalClass;
+        String principalName;
+
+        set = new CredOwner[count];
+        for (int index = 0, i, j; index < count; beg = j + 2, index++) {
+            i = name.indexOf(' ', beg);
+            j = name.indexOf('"', i + 2);
+
+            principalClass = name.substring(beg, i);
+            principalName = name.substring(i + 2, j);
+
+            CredOwner element = new CredOwner(principalClass, principalName);
+            // check for duplicate elements
+            boolean found = false;
+            for (int ii = 0; ii < offset; ii++) {
+                if (set[ii].equals(element)) {
+                    found = true;
+                    break;
+                }
+            }
+            if (!found) {
+                set[offset++] = element;
+            }
+        }
+    }
+
+    private void readObject(ObjectInputStream ois) throws IOException, ClassNotFoundException {
+        ois.defaultReadObject();
+        initTargetName(getName());
+    }
+
+    /**
+     * Returns the principal's classes and names associated with this {@code
+     * PrivateCredentialPermission} as a two dimensional array. The first
+     * dimension of the array corresponds to the number of principals. The
+     * second dimension defines either the name of the {@code PrincipalClass}
+     * [x][0] or the value of {@code PrincipalName} [x][1].
+     * <p>
+     * This corresponds to the the target name's syntax:
+     *
+     * <pre>
+     * targetName = CredentialClass {PrincipalClass &quot;PrincipalName&quot;}*
+     * </pre>
+     *
+     * @return the principal classes and names associated with this {@code
+     *         PrivateCredentialPermission}.
+     */
+    public String[][] getPrincipals() {
+
+        String[][] s = new String[offset][2];
+
+        for (int i = 0; i < s.length; i++) {
+            s[i][0] = set[i].principalClass;
+            s[i][1] = set[i].principalName;
+        }
+        return s;
+    }
+
+    @Override
+    public String getActions() {
+        return READ;
+    }
+
+    /**
+     * Returns the class name of the credential associated with this permission.
+     *
+     * @return the class name of the credential associated with this permission.
+     */
+    public String getCredentialClass() {
+        return credentialClass;
+    }
+
+    @Override
+    public int hashCode() {
+        int hash = 0;
+        for (int i = 0; i < offset; i++) {
+            hash = hash + set[i].hashCode();
+        }
+        return getCredentialClass().hashCode() + hash;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (obj == this) {
+            return true;
+        }
+
+        if (obj == null || this.getClass() != obj.getClass()) {
+            return false;
+        }
+
+        PrivateCredentialPermission that = (PrivateCredentialPermission) obj;
+
+        return credentialClass.equals(that.credentialClass) && (offset == that.offset)
+                && sameMembers(set, that.set, offset);
+    }
+
+    @Override
+    public boolean implies(Permission permission) {
+
+        if (permission == null || this.getClass() != permission.getClass()) {
+            return false;
+        }
+
+        PrivateCredentialPermission that = (PrivateCredentialPermission) permission;
+
+        if (!("*".equals(credentialClass) || credentialClass //$NON-NLS-1$
+                .equals(that.getCredentialClass()))) {
+            return false;
+        }
+
+        if (that.offset == 0) {
+            return true;
+        }
+
+        CredOwner[] thisCo = set;
+        CredOwner[] thatCo = that.set;
+        int thisPrincipalsSize = offset;
+        int thatPrincipalsSize = that.offset;
+        for (int i = 0, j; i < thisPrincipalsSize; i++) {
+            for (j = 0; j < thatPrincipalsSize; j++) {
+                if (thisCo[i].implies(thatCo[j])) {
+                    break;
+                }
+            }
+            if (j == thatCo.length) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    @Override
+    public PermissionCollection newPermissionCollection() {
+        return null;
+    }
+
+    /**
+     * Returns true if the two arrays have the same length, and every member of
+     * one array is contained in another array
+     */
+    private boolean sameMembers(Object[] ar1, Object[] ar2, int length) {
+        if (ar1 == null && ar2 == null) {
+            return true;
+        }
+        if (ar1 == null || ar2 == null) {
+            return false;
+        }
+        boolean found;
+        for (int i = 0; i < length; i++) {
+            found = false;
+            for (int j = 0; j < length; j++) {
+                if (ar1[i].equals(ar2[j])) {
+                    found = true;
+                    break;
+                }
+            }
+            if (!found) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    private static final class CredOwner implements Serializable {
+
+        private static final long serialVersionUID = -5607449830436408266L;
+
+        String principalClass;
+
+        String principalName;
+
+        // whether class name contains wildcards
+        private transient boolean isClassWildcard;
+
+        // whether pname contains wildcards
+        private transient boolean isPNameWildcard;
+
+        // Creates a new CredOwner with the specified Principal Class and Principal Name 
+        CredOwner(String principalClass, String principalName) {
+            super();
+            if ("*".equals(principalClass)) { //$NON-NLS-1$
+                isClassWildcard = true;
+            }
+
+            if ("*".equals(principalName)) { //$NON-NLS-1$
+                isPNameWildcard = true;
+            }
+
+            if (isClassWildcard && !isPNameWildcard) {
+                throw new IllegalArgumentException("auth.12"); //$NON-NLS-1$
+            }
+
+            this.principalClass = principalClass;
+            this.principalName = principalName;
+        }
+
+        // Checks if this CredOwner implies the specified Object. 
+        boolean implies(Object obj) {
+            if (obj == this) {
+                return true;
+            }
+
+            CredOwner co = (CredOwner) obj;
+
+            if (isClassWildcard || principalClass.equals(co.principalClass)) {
+                if (isPNameWildcard || principalName.equals(co.principalName)) {
+                    return true;
+                }
+            }
+            return false;
+        }
+
+        // Checks two CredOwner objects for equality. 
+        @Override
+        public boolean equals(Object obj) {
+            if (obj == this) {
+                return true;
+            }
+            if (obj instanceof CredOwner) {
+                CredOwner that = (CredOwner) obj;
+                return principalClass.equals(that.principalClass)
+                    && principalName.equals(that.principalName);
+            }
+            return false;
+        }
+
+        // Returns the hash code value for this object.
+        @Override
+        public int hashCode() {
+            return principalClass.hashCode() + principalName.hashCode();
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/RefreshFailedException.java b/src/org/apache/harmony/javax/security/auth/RefreshFailedException.java
new file mode 100644
index 0000000..71bcc6b
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/RefreshFailedException.java
@@ -0,0 +1,31 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+public class RefreshFailedException extends Exception {
+
+    private static final long serialVersionUID = 5058444488565265840L;
+
+    public RefreshFailedException() {
+        super();
+    }
+
+    public RefreshFailedException(String message) {
+        super(message);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/Refreshable.java b/src/org/apache/harmony/javax/security/auth/Refreshable.java
new file mode 100644
index 0000000..90b00cb
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/Refreshable.java
@@ -0,0 +1,26 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+public interface Refreshable {
+
+    void refresh() throws RefreshFailedException;
+
+    boolean isCurrent();
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/Subject.java b/src/org/apache/harmony/javax/security/auth/Subject.java
new file mode 100644
index 0000000..142686e
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/Subject.java
@@ -0,0 +1,782 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+import java.security.AccessControlContext;
+import java.security.AccessController;
+import java.security.DomainCombiner;
+import java.security.Permission;
+import java.security.Principal;
+import java.security.PrivilegedAction;
+import java.security.PrivilegedActionException;
+import java.security.PrivilegedExceptionAction;
+import java.security.ProtectionDomain;
+import java.util.AbstractSet;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.Set;
+
+
+
+/**
+ * The central class of the {@code javax.security.auth} package representing an
+ * authenticated user or entity (both referred to as "subject"). IT defines also
+ * the static methods that allow code to be run, and do modifications according
+ * to the subject's permissions.
+ * <p>
+ * A subject has the following features:
+ * <ul>
+ * <li>A set of {@code Principal} objects specifying the identities bound to a
+ * {@code Subject} that distinguish it.</li>
+ * <li>Credentials (public and private) such as certificates, keys, or
+ * authentication proofs such as tickets</li>
+ * </ul>
+ */
+public final class Subject implements Serializable {
+
+    private static final long serialVersionUID = -8308522755600156056L;
+    
+    private static final AuthPermission _AS = new AuthPermission("doAs"); //$NON-NLS-1$
+
+    private static final AuthPermission _AS_PRIVILEGED = new AuthPermission(
+            "doAsPrivileged"); //$NON-NLS-1$
+
+    private static final AuthPermission _SUBJECT = new AuthPermission(
+            "getSubject"); //$NON-NLS-1$
+
+    private static final AuthPermission _PRINCIPALS = new AuthPermission(
+            "modifyPrincipals"); //$NON-NLS-1$
+
+    private static final AuthPermission _PRIVATE_CREDENTIALS = new AuthPermission(
+            "modifyPrivateCredentials"); //$NON-NLS-1$
+
+    private static final AuthPermission _PUBLIC_CREDENTIALS = new AuthPermission(
+            "modifyPublicCredentials"); //$NON-NLS-1$
+
+    private static final AuthPermission _READ_ONLY = new AuthPermission(
+            "setReadOnly"); //$NON-NLS-1$
+
+    private final Set<Principal> principals;
+
+    private boolean readOnly;
+    
+    // set of private credentials
+    private transient SecureSet<Object> privateCredentials;
+
+    // set of public credentials
+    private transient SecureSet<Object> publicCredentials;
+    
+    /**
+     * The default constructor initializing the sets of public and private
+     * credentials and principals with the empty set.
+     */
+    public Subject() {
+        super();
+        principals = new SecureSet<Principal>(_PRINCIPALS);
+        publicCredentials = new SecureSet<Object>(_PUBLIC_CREDENTIALS);
+        privateCredentials = new SecureSet<Object>(_PRIVATE_CREDENTIALS);
+
+        readOnly = false;
+    }
+
+    /**
+     * The constructor for the subject, setting its public and private
+     * credentials and principals according to the arguments.
+     *
+     * @param readOnly
+     *            {@code true} if this {@code Subject} is read-only, thus
+     *            preventing any modifications to be done.
+     * @param subjPrincipals
+     *            the set of Principals that are attributed to this {@code
+     *            Subject}.
+     * @param pubCredentials
+     *            the set of public credentials that distinguish this {@code
+     *            Subject}.
+     * @param privCredentials
+     *            the set of private credentials that distinguish this {@code
+     *            Subject}.
+     */
+    public Subject(boolean readOnly, Set<? extends Principal> subjPrincipals,
+            Set<?> pubCredentials, Set<?> privCredentials) {
+
+        if (subjPrincipals == null || pubCredentials == null || privCredentials == null) {
+            throw new NullPointerException();
+        }
+
+        principals = new SecureSet<Principal>(_PRINCIPALS, subjPrincipals);
+        publicCredentials = new SecureSet<Object>(_PUBLIC_CREDENTIALS, pubCredentials);
+        privateCredentials = new SecureSet<Object>(_PRIVATE_CREDENTIALS, privCredentials);
+
+        this.readOnly = readOnly;
+    }
+
+    /**
+     * Runs the code defined by {@code action} using the permissions granted to
+     * the {@code Subject} itself and to the code as well.
+     *
+     * @param subject
+     *            the distinguished {@code Subject}.
+     * @param action
+     *            the code to be run.
+     * @return the {@code Object} returned when running the {@code action}.
+     */
+    @SuppressWarnings("unchecked")
+    public static Object doAs(Subject subject, PrivilegedAction action) {
+
+        checkPermission(_AS);
+
+        return doAs_PrivilegedAction(subject, action, AccessController.getContext());
+    }
+
+    /**
+     * Run the code defined by {@code action} using the permissions granted to
+     * the {@code Subject} and to the code itself, additionally providing a more
+     * specific context.
+     *
+     * @param subject
+     *            the distinguished {@code Subject}.
+     * @param action
+     *            the code to be run.
+     * @param context
+     *            the specific context in which the {@code action} is invoked.
+     *            if {@code null} a new {@link AccessControlContext} is
+     *            instantiated.
+     * @return the {@code Object} returned when running the {@code action}.
+     */
+    @SuppressWarnings("unchecked")
+    public static Object doAsPrivileged(Subject subject, PrivilegedAction action,
+            AccessControlContext context) {
+
+        checkPermission(_AS_PRIVILEGED);
+
+        if (context == null) {
+            return doAs_PrivilegedAction(subject, action, new AccessControlContext(
+                    new ProtectionDomain[0]));
+        }
+        return doAs_PrivilegedAction(subject, action, context);
+    }
+
+    // instantiates a new context and passes it to AccessController
+    @SuppressWarnings("unchecked")
+    private static Object doAs_PrivilegedAction(Subject subject, PrivilegedAction action,
+            final AccessControlContext context) {
+
+        AccessControlContext newContext;
+
+        final SubjectDomainCombiner combiner;
+        if (subject == null) {
+            // performance optimization
+            // if subject is null there is nothing to combine
+            combiner = null;
+        } else {
+            combiner = new SubjectDomainCombiner(subject);
+        }
+
+        PrivilegedAction dccAction = new PrivilegedAction() {
+            public Object run() {
+
+                return new AccessControlContext(context, combiner);
+            }
+        };
+
+        newContext = (AccessControlContext) AccessController.doPrivileged(dccAction);
+
+        return AccessController.doPrivileged(action, newContext);
+    }
+
+    /**
+     * Runs the code defined by {@code action} using the permissions granted to
+     * the subject and to the code itself.
+     *
+     * @param subject
+     *            the distinguished {@code Subject}.
+     * @param action
+     *            the code to be run.
+     * @return the {@code Object} returned when running the {@code action}.
+     * @throws PrivilegedActionException
+     *             if running the {@code action} throws an exception.
+     */
+    @SuppressWarnings("unchecked")
+    public static Object doAs(Subject subject, PrivilegedExceptionAction action)
+            throws PrivilegedActionException {
+
+        checkPermission(_AS);
+
+        return doAs_PrivilegedExceptionAction(subject, action, AccessController.getContext());
+    }
+
+    /**
+     * Runs the code defined by {@code action} using the permissions granted to
+     * the subject and to the code itself, additionally providing a more
+     * specific context.
+     *
+     * @param subject
+     *            the distinguished {@code Subject}.
+     * @param action
+     *            the code to be run.
+     * @param context
+     *            the specific context in which the {@code action} is invoked.
+     *            if {@code null} a new {@link AccessControlContext} is
+     *            instantiated.
+     * @return the {@code Object} returned when running the {@code action}.
+     * @throws PrivilegedActionException
+     *             if running the {@code action} throws an exception.
+     */
+    @SuppressWarnings("unchecked")
+    public static Object doAsPrivileged(Subject subject,
+            PrivilegedExceptionAction action, AccessControlContext context)
+            throws PrivilegedActionException {
+
+        checkPermission(_AS_PRIVILEGED);
+
+        if (context == null) {
+            return doAs_PrivilegedExceptionAction(subject, action,
+                    new AccessControlContext(new ProtectionDomain[0]));
+        }
+        return doAs_PrivilegedExceptionAction(subject, action, context);
+    }
+
+    // instantiates a new context and passes it to AccessController
+    @SuppressWarnings("unchecked")
+    private static Object doAs_PrivilegedExceptionAction(Subject subject,
+            PrivilegedExceptionAction action, final AccessControlContext context)
+            throws PrivilegedActionException {
+
+        AccessControlContext newContext;
+
+        final SubjectDomainCombiner combiner;
+        if (subject == null) {
+            // performance optimization
+            // if subject is null there is nothing to combine
+            combiner = null;
+        } else {
+            combiner = new SubjectDomainCombiner(subject);
+        }
+
+        PrivilegedAction<AccessControlContext> dccAction = new PrivilegedAction<AccessControlContext>() {
+            public AccessControlContext run() {
+                return new AccessControlContext(context, combiner);
+            }
+        };
+
+        newContext = AccessController.doPrivileged(dccAction);
+
+        return AccessController.doPrivileged(action, newContext);
+    }
+
+    /**
+     * Checks two Subjects for equality. More specifically if the principals,
+     * public and private credentials are equal, equality for two {@code
+     * Subjects} is implied.
+     *
+     * @param obj
+     *            the {@code Object} checked for equality with this {@code
+     *            Subject}.
+     * @return {@code true} if the specified {@code Subject} is equal to this
+     *         one.
+     */
+    @Override
+    public boolean equals(Object obj) {
+
+        if (this == obj) {
+            return true;
+        }
+
+        if (obj == null || this.getClass() != obj.getClass()) {
+            return false;
+        }
+
+        Subject that = (Subject) obj;
+
+        if (principals.equals(that.principals)
+                && publicCredentials.equals(that.publicCredentials)
+                && privateCredentials.equals(that.privateCredentials)) {
+            return true;
+        }
+        return false;
+    }
+
+    /**
+     * Returns this {@code Subject}'s {@link Principal}.
+     *
+     * @return this {@code Subject}'s {@link Principal}.
+     */
+    public Set<Principal> getPrincipals() {
+        return principals;
+    }
+
+
+    /**
+     * Returns this {@code Subject}'s {@link Principal} which is a subclass of
+     * the {@code Class} provided.
+     *
+     * @param c
+     *            the {@code Class} as a criteria which the {@code Principal}
+     *            returned must satisfy.
+     * @return this {@code Subject}'s {@link Principal}. Modifications to the
+     *         returned set of {@code Principal}s do not affect this {@code
+     *         Subject}'s set.
+     */
+    public <T extends Principal> Set<T> getPrincipals(Class<T> c) {
+        return ((SecureSet<Principal>) principals).get(c);
+    }
+
+    /**
+     * Returns the private credentials associated with this {@code Subject}.
+     *
+     * @return the private credentials associated with this {@code Subject}.
+     */
+    public Set<Object> getPrivateCredentials() {
+        return privateCredentials;
+    }
+
+    /**
+     * Returns this {@code Subject}'s private credentials which are a subclass
+     * of the {@code Class} provided.
+     *
+     * @param c
+     *            the {@code Class} as a criteria which the private credentials
+     *            returned must satisfy.
+     * @return this {@code Subject}'s private credentials. Modifications to the
+     *         returned set of credentials do not affect this {@code Subject}'s
+     *         credentials.
+     */
+    public <T> Set<T> getPrivateCredentials(Class<T> c) {
+        return privateCredentials.get(c);
+    }
+
+    /**
+     * Returns the public credentials associated with this {@code Subject}.
+     *
+     * @return the public credentials associated with this {@code Subject}.
+     */
+    public Set<Object> getPublicCredentials() {
+        return publicCredentials;
+    }
+
+
+    /**
+     * Returns this {@code Subject}'s public credentials which are a subclass of
+     * the {@code Class} provided.
+     *
+     * @param c
+     *            the {@code Class} as a criteria which the public credentials
+     *            returned must satisfy.
+     * @return this {@code Subject}'s public credentials. Modifications to the
+     *         returned set of credentials do not affect this {@code Subject}'s
+     *         credentials.
+     */
+    public <T> Set<T> getPublicCredentials(Class<T> c) {
+        return publicCredentials.get(c);
+    }
+
+    /**
+     * Returns a hash code of this {@code Subject}.
+     *
+     * @return a hash code of this {@code Subject}.
+     */
+    @Override
+    public int hashCode() {
+        return principals.hashCode() + privateCredentials.hashCode()
+                + publicCredentials.hashCode();
+    }
+
+    /**
+     * Prevents from modifications being done to the credentials and {@link
+     * Principal} sets. After setting it to read-only this {@code Subject} can
+     * not be made writable again. The destroy method on the credentials still
+     * works though.
+     */
+    public void setReadOnly() {
+        checkPermission(_READ_ONLY);
+
+        readOnly = true;
+    }
+
+    /**
+     * Returns whether this {@code Subject} is read-only or not.
+     *
+     * @return whether this {@code Subject} is read-only or not.
+     */
+    public boolean isReadOnly() {
+        return readOnly;
+    }
+
+    /**
+     * Returns a {@code String} representation of this {@code Subject}.
+     *
+     * @return a {@code String} representation of this {@code Subject}.
+     */
+    @Override
+    public String toString() {
+
+        StringBuilder buf = new StringBuilder("Subject:\n"); //$NON-NLS-1$
+
+        Iterator<?> it = principals.iterator();
+        while (it.hasNext()) {
+            buf.append("\tPrincipal: "); //$NON-NLS-1$
+            buf.append(it.next());
+            buf.append('\n');
+        }
+
+        it = publicCredentials.iterator();
+        while (it.hasNext()) {
+            buf.append("\tPublic Credential: "); //$NON-NLS-1$
+            buf.append(it.next());
+            buf.append('\n');
+        }
+
+        int offset = buf.length() - 1;
+        it = privateCredentials.iterator();
+        try {
+            while (it.hasNext()) {
+                buf.append("\tPrivate Credential: "); //$NON-NLS-1$
+                buf.append(it.next());
+                buf.append('\n');
+            }
+        } catch (SecurityException e) {
+            buf.delete(offset, buf.length());
+            buf.append("\tPrivate Credentials: no accessible information\n"); //$NON-NLS-1$
+        }
+        return buf.toString();
+    }
+
+    private void readObject(ObjectInputStream in) throws IOException,
+            ClassNotFoundException {
+
+        in.defaultReadObject();
+
+        publicCredentials = new SecureSet<Object>(_PUBLIC_CREDENTIALS);
+        privateCredentials = new SecureSet<Object>(_PRIVATE_CREDENTIALS);
+    }
+
+    private void writeObject(ObjectOutputStream out) throws IOException {
+        out.defaultWriteObject();
+    }
+
+    /**
+     * Returns the {@code Subject} that was last associated with the {@code
+     * context} provided as argument.
+     *
+     * @param context
+     *            the {@code context} that was associated with the
+     *            {@code Subject}.
+     * @return the {@code Subject} that was last associated with the {@code
+     *         context} provided as argument.
+     */
+    public static Subject getSubject(final AccessControlContext context) {
+        checkPermission(_SUBJECT);
+        if (context == null) {
+            throw new NullPointerException("auth.09"); //$NON-NLS-1$
+        }
+        PrivilegedAction<DomainCombiner> action = new PrivilegedAction<DomainCombiner>() {
+            public DomainCombiner run() {
+                return context.getDomainCombiner();
+            }
+        };
+        DomainCombiner combiner = AccessController.doPrivileged(action);
+
+        if ((combiner == null) || !(combiner instanceof SubjectDomainCombiner)) {
+            return null;
+        }
+        return ((SubjectDomainCombiner) combiner).getSubject();
+    }
+
+    // checks passed permission
+    private static void checkPermission(Permission p) {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null) {
+            sm.checkPermission(p);
+        }
+    }
+
+    // FIXME is used only in two places. remove?
+    private void checkState() {
+        if (readOnly) {
+            throw new IllegalStateException("auth.0A"); //$NON-NLS-1$
+        }
+    }
+
+    private final class SecureSet<SST> extends AbstractSet<SST> implements Serializable {
+
+        /**
+         * Compatibility issue: see comments for setType variable
+         */
+        private static final long serialVersionUID = 7911754171111800359L;
+
+        private LinkedList<SST> elements;
+
+        /*
+         * Is used to define a set type for serialization.
+         * 
+         * A type can be principal, priv. or pub. credential set. The spec.
+         * doesn't clearly says that priv. and pub. credential sets can be
+         * serialized and what classes they are. It is only possible to figure
+         * out from writeObject method comments that priv. credential set is
+         * serializable and it is an instance of SecureSet class. So pub.
+         * credential was implemented by analogy
+         * 
+         * Compatibility issue: the class follows its specified serial form.
+         * Also according to the serialization spec. adding new field is a
+         * compatible change. So is ok for principal set (because the default
+         * value for integer is zero). But priv. or pub. credential set it is
+         * not compatible because most probably other implementations resolve
+         * this issue in other way
+         */
+        private int setType;
+
+        // Defines principal set for serialization.
+        private static final int SET_Principal = 0;
+
+        // Defines private credential set for serialization.
+        private static final int SET_PrivCred = 1;
+
+        // Defines public credential set for serialization.
+        private static final int SET_PubCred = 2;
+
+        // permission required to modify set
+        private transient AuthPermission permission;
+
+        protected SecureSet(AuthPermission perm) {
+            permission = perm;
+            elements = new LinkedList<SST>();
+        }
+
+        // creates set from specified collection with specified permission
+        // all collection elements are verified before adding
+        protected SecureSet(AuthPermission perm, Collection<? extends SST> s) {
+            this(perm);
+
+            // Subject's constructor receives a Set, we can trusts if a set is from bootclasspath,
+            // and not to check whether it contains duplicates or not
+            boolean trust = s.getClass().getClassLoader() == null; 
+            
+            Iterator<? extends SST> it = s.iterator();
+            while (it.hasNext()) {
+                SST o = it.next();
+                verifyElement(o);
+                if (trust || !elements.contains(o)) {
+                    elements.add(o);
+                }
+            }
+        }
+
+        // verifies new set element
+        private void verifyElement(Object o) {
+
+            if (o == null) {
+                throw new NullPointerException();
+            }
+            if (permission == _PRINCIPALS && !(Principal.class.isAssignableFrom(o.getClass()))) {
+                throw new IllegalArgumentException("auth.0B"); //$NON-NLS-1$
+            }
+        }
+
+        /*
+         * verifies specified element, checks set state, and security permission
+         * to modify set before adding new element
+         */
+        @Override
+        public boolean add(SST o) {
+
+            verifyElement(o);
+
+            checkState();
+            checkPermission(permission);
+
+            if (!elements.contains(o)) {
+                elements.add(o);
+                return true;
+            }
+            return false;
+        }
+
+        // returns an instance of SecureIterator
+        @Override
+        public Iterator<SST> iterator() {
+
+            if (permission == _PRIVATE_CREDENTIALS) {
+                /*
+                 * private credential set requires iterator with additional
+                 * security check (PrivateCredentialPermission)
+                 */
+                return new SecureIterator(elements.iterator()) {
+                    /*
+                     * checks permission to access next private credential moves
+                     * to the next element even SecurityException was thrown
+                     */
+                    @Override
+                    public SST next() {
+                        SST obj = iterator.next();
+                        checkPermission(new PrivateCredentialPermission(obj
+                                .getClass().getName(), principals));
+                        return obj;
+                    }
+                };
+            }
+            return new SecureIterator(elements.iterator());
+        }
+
+        @Override
+        public boolean retainAll(Collection<?> c) {
+
+            if (c == null) {
+                throw new NullPointerException();
+            }
+            return super.retainAll(c);
+        }
+
+        @Override
+        public int size() {
+            return elements.size();
+        }
+
+        /**
+         * return set with elements that are instances or subclasses of the
+         * specified class
+         */
+        protected final <E> Set<E> get(final Class<E> c) {
+
+            if (c == null) {
+                throw new NullPointerException();
+            }
+
+            AbstractSet<E> s = new AbstractSet<E>() {
+                private LinkedList<E> elements = new LinkedList<E>();
+
+                @Override
+                public boolean add(E o) {
+
+                    if (!c.isAssignableFrom(o.getClass())) {
+                        throw new IllegalArgumentException(
+                                "auth.0C " + c.getName()); //$NON-NLS-1$
+                    }
+
+                    if (elements.contains(o)) {
+                        return false;
+                    }
+                    elements.add(o);
+                    return true;
+                }
+
+                @Override
+                public Iterator<E> iterator() {
+                    return elements.iterator();
+                }
+
+                @Override
+                public boolean retainAll(Collection<?> c) {
+
+                    if (c == null) {
+                        throw new NullPointerException();
+                    }
+                    return super.retainAll(c);
+                }
+
+                @Override
+                public int size() {
+                    return elements.size();
+                }
+            };
+
+            // FIXME must have permissions for requested priv. credentials
+            for (Iterator<SST> it = iterator(); it.hasNext();) {
+                SST o = it.next();
+                if (c.isAssignableFrom(o.getClass())) {
+                    s.add(c.cast(o));
+                }
+            }
+            return s;
+        }
+
+        private void readObject(ObjectInputStream in) throws IOException,
+                ClassNotFoundException {
+            in.defaultReadObject();
+
+            switch (setType) {
+            case SET_Principal:
+                permission = _PRINCIPALS;
+                break;
+            case SET_PrivCred:
+                permission = _PRIVATE_CREDENTIALS;
+                break;
+            case SET_PubCred:
+                permission = _PUBLIC_CREDENTIALS;
+                break;
+            default:
+                throw new IllegalArgumentException();
+            }
+
+            Iterator<SST> it = elements.iterator();
+            while (it.hasNext()) {
+                verifyElement(it.next());
+            }
+        }
+
+        private void writeObject(ObjectOutputStream out) throws IOException {
+
+            if (permission == _PRIVATE_CREDENTIALS) {
+                // does security check for each private credential
+                for (Iterator<SST> it = iterator(); it.hasNext();) {
+                    it.next();
+                }
+                setType = SET_PrivCred;
+            } else if (permission == _PRINCIPALS) {
+                setType = SET_Principal;
+            } else {
+                setType = SET_PubCred;
+            }
+
+            out.defaultWriteObject();
+        }
+
+        /**
+         * Represents iterator for subject's secure set
+         */
+        private class SecureIterator implements Iterator<SST> {
+            protected Iterator<SST> iterator;
+
+            protected SecureIterator(Iterator<SST> iterator) {
+                this.iterator = iterator;
+            }
+
+            public boolean hasNext() {
+                return iterator.hasNext();
+            }
+
+            public SST next() {
+                return iterator.next();
+            }
+
+            /**
+             * checks set state, and security permission to modify set before
+             * removing current element
+             */
+            public void remove() {
+                checkState();
+                checkPermission(permission);
+                iterator.remove();
+            }
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/SubjectDomainCombiner.java b/src/org/apache/harmony/javax/security/auth/SubjectDomainCombiner.java
new file mode 100644
index 0000000..edbb672
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/SubjectDomainCombiner.java
@@ -0,0 +1,123 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth;
+
+import java.security.DomainCombiner;
+import java.security.Principal;
+import java.security.ProtectionDomain;
+import java.util.Set;
+
+/**
+ * Merges permissions based on code source and code signers with permissions
+ * granted to the specified {@link Subject}.
+ */
+public class SubjectDomainCombiner implements DomainCombiner {
+
+    // subject to be associated
+    private Subject subject;
+
+    // permission required to get a subject object
+    private static final AuthPermission _GET = new AuthPermission(
+            "getSubjectFromDomainCombiner"); //$NON-NLS-1$
+
+    /**
+     * Creates a domain combiner for the entity provided in {@code subject}.
+     *
+     * @param subject
+     *            the entity to which this domain combiner is associated.
+     */
+    public SubjectDomainCombiner(Subject subject) {
+        super();
+        if (subject == null) {
+            throw new NullPointerException();
+        }
+        this.subject = subject;
+    }
+
+    /**
+     * Returns the entity to which this domain combiner is associated.
+     *
+     * @return the entity to which this domain combiner is associated.
+     */
+    public Subject getSubject() {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null) {
+            sm.checkPermission(_GET);
+        }
+
+        return subject;
+    }
+
+    /**
+     * Merges the {@code ProtectionDomain} with the {@code Principal}s
+     * associated with the subject of this {@code SubjectDomainCombiner}.
+     *
+     * @param currentDomains
+     *            the {@code ProtectionDomain}s associated with the context of
+     *            the current thread. The domains must be sorted according to
+     *            the execution order, the most recent residing at the
+     *            beginning.
+     * @param assignedDomains
+     *            the {@code ProtectionDomain}s from the parent thread based on
+     *            code source and signers.
+     * @return a single {@code ProtectionDomain} array computed from the two
+     *         provided arrays, or {@code null}.
+     * @see ProtectionDomain
+     */
+    public ProtectionDomain[] combine(ProtectionDomain[] currentDomains,
+            ProtectionDomain[] assignedDomains) {
+        // get array length for combining protection domains
+        int len = 0;
+        if (currentDomains != null) {
+            len += currentDomains.length;
+        }
+        if (assignedDomains != null) {
+            len += assignedDomains.length;
+        }
+        if (len == 0) {
+            return null;
+        }
+
+        ProtectionDomain[] pd = new ProtectionDomain[len];
+
+        // for each current domain substitute set of principal with subject's
+        int cur = 0;
+        if (currentDomains != null) {
+
+            Set<Principal> s = subject.getPrincipals();
+            Principal[] p = s.toArray(new Principal[s.size()]);
+
+            for (cur = 0; cur < currentDomains.length; cur++) {
+                if (currentDomains[cur] != null) {
+                    ProtectionDomain newPD;
+                    newPD = new ProtectionDomain(currentDomains[cur].getCodeSource(),
+                            currentDomains[cur].getPermissions(), currentDomains[cur]
+                                    .getClassLoader(), p);
+                    pd[cur] = newPD;
+                }
+            }
+        }
+
+        // copy assigned domains
+        if (assignedDomains != null) {
+            System.arraycopy(assignedDomains, 0, pd, cur, assignedDomains.length);
+        }
+
+        return pd;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/Callback.java b/src/org/apache/harmony/javax/security/auth/callback/Callback.java
new file mode 100644
index 0000000..8fd745c
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/Callback.java
@@ -0,0 +1,25 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+/**
+ * Defines an empty base interface for all {@code Callback}s used during
+ * authentication.
+ */
+public interface Callback {
+}
\ No newline at end of file
diff --git a/src/org/apache/harmony/javax/security/auth/callback/CallbackHandler.java b/src/org/apache/harmony/javax/security/auth/callback/CallbackHandler.java
new file mode 100644
index 0000000..d09fafa
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/CallbackHandler.java
@@ -0,0 +1,54 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.IOException;
+
+/**
+ * Needs to be implemented by classes that want to handle authentication
+ * {@link Callback}s. A single method {@link #handle(Callback[])} must be
+ * provided that checks the type of the incoming {@code Callback}s and reacts
+ * accordingly. {@code CallbackHandler}s can be installed per application. It is
+ * also possible to configure a system-default {@code CallbackHandler} by
+ * setting the {@code auth.login.defaultCallbackHandler} property in the
+ * standard {@code security.properties} file.
+ */
+public interface CallbackHandler {
+
+    /**
+     * Handles the actual {@link Callback}. A {@code CallbackHandler} needs to
+     * implement this method. In the method, it is free to select which {@code
+     * Callback}s it actually wants to handle and in which way. For example, a
+     * console-based {@code CallbackHandler} might choose to sequentially ask
+     * the user for login and password, if it implements these {@code Callback}
+     * s, whereas a GUI-based one might open a single dialog window for both
+     * values. If a {@code CallbackHandler} is not able to handle a specific
+     * {@code Callback}, it needs to throw an
+     * {@link UnsupportedCallbackException}.
+     *
+     * @param callbacks
+     *            the array of {@code Callback}s that need handling
+     * @throws IOException
+     *             if an I/O related error occurs
+     * @throws UnsupportedCallbackException
+     *             if the {@code CallbackHandler} is not able to handle a
+     *             specific {@code Callback}
+     */
+    void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException;
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/ChoiceCallback.java b/src/org/apache/harmony/javax/security/auth/callback/ChoiceCallback.java
new file mode 100644
index 0000000..1e53fb6
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/ChoiceCallback.java
@@ -0,0 +1,109 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+
+
+
+public class ChoiceCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = -3975664071579892167L;
+
+    private int defaultChoice;
+
+    private String prompt;
+
+    private boolean multipleSelectionsAllowed;
+
+    private String[] choices;
+
+    private int[] selections;
+
+    private void setChoices(String[] choices) {
+        if (choices == null || choices.length == 0) {
+            throw new IllegalArgumentException("auth.1C"); //$NON-NLS-1$
+        }
+        for (int i = 0; i < choices.length; i++) {
+            if (choices[i] == null || choices[i].length() == 0) {
+                throw new IllegalArgumentException("auth.1C"); //$NON-NLS-1$
+            }
+        }
+        //FIXME: System.arraycopy(choices, 0 , new String[choices.length], 0, choices.length);
+        this.choices = choices;
+
+    }
+
+    private void setPrompt(String prompt) {
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+        this.prompt = prompt;
+    }
+
+    private void setDefaultChoice(int defaultChoice) {
+        if (0 > defaultChoice || defaultChoice >= choices.length) {
+            throw new IllegalArgumentException("auth.1D"); //$NON-NLS-1$
+        }
+        this.defaultChoice = defaultChoice;
+    }
+
+    public ChoiceCallback(String prompt, String[] choices, int defaultChoice,
+            boolean multipleSelectionsAllowed) {
+        super();
+        setPrompt(prompt);
+        setChoices(choices);
+        setDefaultChoice(defaultChoice);
+        this.multipleSelectionsAllowed = multipleSelectionsAllowed;
+    }
+
+    public boolean allowMultipleSelections() {
+        return multipleSelectionsAllowed;
+    }
+
+    public String[] getChoices() {
+        return choices;
+    }
+
+    public int getDefaultChoice() {
+        return defaultChoice;
+    }
+
+    public String getPrompt() {
+        return prompt;
+    }
+
+    public int[] getSelectedIndexes() {
+        return selections;
+    }
+
+    public void setSelectedIndex(int selection) {
+        this.selections = new int[1];
+        this.selections[0] = selection;
+    }
+
+    public void setSelectedIndexes(int[] selections) {
+        if (!multipleSelectionsAllowed) {
+            throw new UnsupportedOperationException();
+        }
+        this.selections = selections;
+        //FIXME: 
+        // this.selections = new int[selections.length]
+        //System.arraycopy(selections, 0, this.selections, 0, this.selections.length);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/ConfirmationCallback.java b/src/org/apache/harmony/javax/security/auth/callback/ConfirmationCallback.java
new file mode 100644
index 0000000..a1893f3
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/ConfirmationCallback.java
@@ -0,0 +1,234 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+
+
+
+public class ConfirmationCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = -9095656433782481624L;
+
+    public static final int YES = 0; // default options
+
+    public static final int NO = 1;
+
+    public static final int CANCEL = 2;
+
+    public static final int OK = 3;
+
+    public static final int YES_NO_OPTION = 0; // options type
+
+    public static final int YES_NO_CANCEL_OPTION = 1;
+
+    public static final int OK_CANCEL_OPTION = 2;
+
+    public static final int UNSPECIFIED_OPTION = -1;
+
+    public static final int INFORMATION = 0; // messages type
+
+    public static final int WARNING = 1;
+
+    public static final int ERROR = 2;
+
+    private String prompt;
+
+    private int messageType;
+
+    private int optionType = UNSPECIFIED_OPTION;
+
+    private int defaultOption;
+
+    private String[] options;
+
+    private int selection;
+
+    public ConfirmationCallback(int messageType, int optionType, int defaultOption) {
+        super();
+        if (messageType > ERROR || messageType < INFORMATION) {
+            throw new IllegalArgumentException("auth.16"); //$NON-NLS-1$
+        }
+
+        switch (optionType) {
+            case YES_NO_OPTION:
+                if (defaultOption != YES && defaultOption != NO) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            case YES_NO_CANCEL_OPTION:
+                if (defaultOption != YES && defaultOption != NO && defaultOption != CANCEL) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            case OK_CANCEL_OPTION:
+                if (defaultOption != OK && defaultOption != CANCEL) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            default:
+                throw new IllegalArgumentException("auth.18"); //$NON-NLS-1$
+        }
+        this.messageType = messageType;
+        this.optionType = optionType;
+        this.defaultOption = defaultOption;
+    }
+
+    public ConfirmationCallback(int messageType, String[] options, int defaultOption) {
+        super();
+        if (messageType > ERROR || messageType < INFORMATION) {
+            throw new IllegalArgumentException("auth.16"); //$NON-NLS-1$
+        }
+
+        if (options == null || options.length == 0) {
+            throw new IllegalArgumentException("auth.1A"); //$NON-NLS-1$
+        }
+        for (int i = 0; i < options.length; i++) {
+            if (options[i] == null || options[i].length() == 0) {
+                throw new IllegalArgumentException("auth.1A"); //$NON-NLS-1$
+            }
+        }
+        if (0 > defaultOption || defaultOption >= options.length) {
+            throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+        }
+        // FIXME:System.arraycopy(options, 0 , new String[this.options.length],
+        // 0, this.options.length);
+        this.options = options;
+        this.defaultOption = defaultOption;
+        this.messageType = messageType;
+    }
+
+    public ConfirmationCallback(String prompt, int messageType, int optionType,
+            int defaultOption) {
+        super();
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+
+        if (messageType > ERROR || messageType < INFORMATION) {
+            throw new IllegalArgumentException("auth.16"); //$NON-NLS-1$
+        }
+
+        switch (optionType) {
+            case YES_NO_OPTION:
+                if (defaultOption != YES && defaultOption != NO) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            case YES_NO_CANCEL_OPTION:
+                if (defaultOption != YES && defaultOption != NO && defaultOption != CANCEL) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            case OK_CANCEL_OPTION:
+                if (defaultOption != OK && defaultOption != CANCEL) {
+                    throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+                }
+                break;
+            default:
+                throw new IllegalArgumentException("auth.18"); //$NON-NLS-1$
+        }
+        this.prompt = prompt;
+        this.messageType = messageType;
+        this.optionType = optionType;
+        this.defaultOption = defaultOption;
+    }
+
+    public ConfirmationCallback(String prompt, int messageType, String[] options,
+            int defaultOption) {
+        super();
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+
+        if (messageType > ERROR || messageType < INFORMATION) {
+            throw new IllegalArgumentException("auth.16"); //$NON-NLS-1$
+        }
+
+        if (options == null || options.length == 0) {
+            throw new IllegalArgumentException("auth.1A"); //$NON-NLS-1$
+        }
+        for (int i = 0; i < options.length; i++) {
+            if (options[i] == null || options[i].length() == 0) {
+                throw new IllegalArgumentException("auth.1A"); //$NON-NLS-1$
+            }
+        }
+        if (0 > defaultOption || defaultOption >= options.length) {
+            throw new IllegalArgumentException("auth.17"); //$NON-NLS-1$
+        }
+        // FIXME:System.arraycopy(options, 0 , new String[this.options.length],
+        // 0, this.options.length);
+        this.options = options;
+        this.defaultOption = defaultOption;
+        this.messageType = messageType;
+        this.prompt = prompt;
+    }
+
+    public String getPrompt() {
+        return prompt;
+    }
+
+    public int getMessageType() {
+        return messageType;
+    }
+
+    public int getDefaultOption() {
+        return defaultOption;
+    }
+
+    public String[] getOptions() {
+        return options;
+    }
+
+    public int getOptionType() {
+        return optionType;
+    }
+
+    public int getSelectedIndex() {
+        return selection;
+    }
+
+    public void setSelectedIndex(int selection) {
+        if (options != null) {
+            if (0 <= selection && selection <= options.length) {
+                this.selection = selection;
+            } else {
+                throw new ArrayIndexOutOfBoundsException("auth.1B"); //$NON-NLS-1$
+            }
+        } else {
+            switch (optionType) {
+                case YES_NO_OPTION:
+                    if (selection != YES && selection != NO) {
+                        throw new IllegalArgumentException("auth.19"); //$NON-NLS-1$
+                    }
+                    break;
+                case YES_NO_CANCEL_OPTION:
+                    if (selection != YES && selection != NO && selection != CANCEL) {
+                        throw new IllegalArgumentException("auth.19"); //$NON-NLS-1$
+                    }
+                    break;
+                case OK_CANCEL_OPTION:
+                    if (selection != OK && selection != CANCEL) {
+                        throw new IllegalArgumentException("auth.19"); //$NON-NLS-1$
+                    }
+                    break;
+            }
+            this.selection = selection;
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/LanguageCallback.java b/src/org/apache/harmony/javax/security/auth/callback/LanguageCallback.java
new file mode 100644
index 0000000..729bb49
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/LanguageCallback.java
@@ -0,0 +1,41 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+import java.util.Locale;
+
+public class LanguageCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = 2019050433478903213L;
+
+    private Locale locale;
+
+    public LanguageCallback() {
+        super();
+    }
+
+    public Locale getLocale() {
+        return locale;
+    }
+
+    public void setLocale(Locale locale) {
+        this.locale = locale;
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/NameCallback.java b/src/org/apache/harmony/javax/security/auth/callback/NameCallback.java
new file mode 100644
index 0000000..97264ef
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/NameCallback.java
@@ -0,0 +1,74 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+
+
+
+public class NameCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = 3770938795909392253L;
+
+    private String prompt;
+
+    private String defaultName;
+
+    private String inputName;
+
+    private void setPrompt(String prompt) {
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+        this.prompt = prompt;
+    }
+
+    private void setDefaultName(String defaultName) {
+        if (defaultName == null || defaultName.length() == 0) {
+            throw new IllegalArgumentException("auth.1E"); //$NON-NLS-1$
+        }
+        this.defaultName = defaultName;
+    }
+
+    public NameCallback(String prompt) {
+        super();
+        setPrompt(prompt);
+    }
+
+    public NameCallback(String prompt, String defaultName) {
+        super();
+        setPrompt(prompt);
+        setDefaultName(defaultName);
+    }
+
+    public String getPrompt() {
+        return prompt;
+    }
+
+    public String getDefaultName() {
+        return defaultName;
+    }
+
+    public void setName(String name) {
+        this.inputName = name;
+    }
+
+    public String getName() {
+        return inputName;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/PasswordCallback.java b/src/org/apache/harmony/javax/security/auth/callback/PasswordCallback.java
new file mode 100644
index 0000000..bd142fc
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/PasswordCallback.java
@@ -0,0 +1,124 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+import java.util.Arrays;
+
+
+
+/**
+ * Is used in conjunction with a {@link CallbackHandler} to retrieve a password
+ * when needed.
+ */
+public class PasswordCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = 2267422647454909926L;
+
+    private String prompt;
+
+    boolean echoOn;
+
+    private char[] inputPassword;
+
+    private void setPrompt(String prompt) throws IllegalArgumentException {
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+        this.prompt = prompt;
+    }
+
+    /**
+     * Creates a new {@code PasswordCallback} instance.
+     *
+     * @param prompt
+     *            the message that should be displayed to the user
+     * @param echoOn
+     *            determines whether the user input should be echoed
+     */
+    public PasswordCallback(String prompt, boolean echoOn) {
+        super();
+        setPrompt(prompt);
+        this.echoOn = echoOn;
+    }
+
+    /**
+     * Returns the prompt that was specified when creating this {@code
+     * PasswordCallback}
+     *
+     * @return the prompt
+     */
+    public String getPrompt() {
+        return prompt;
+    }
+
+    /**
+     * Queries whether this {@code PasswordCallback} expects user input to be
+     * echoed, which is specified during the creation of the object.
+     *
+     * @return {@code true} if (and only if) user input should be echoed
+     */
+    public boolean isEchoOn() {
+        return echoOn;
+    }
+
+    /**
+     * Sets the password. The {@link CallbackHandler} that performs the actual
+     * provisioning or input of the password needs to call this method to hand
+     * back the password to the security service that requested it.
+     *
+     * @param password
+     *            the password. A copy of this is stored, so subsequent changes
+     *            to the input array do not affect the {@code PasswordCallback}.
+     */
+    public void setPassword(char[] password) {
+        if (password == null) {
+            this.inputPassword = password;
+        } else {
+            inputPassword = new char[password.length];
+            System.arraycopy(password, 0, inputPassword, 0, inputPassword.length);
+        }
+    }
+
+    /**
+     * Returns the password. The security service that needs the password
+     * usually calls this method once the {@link CallbackHandler} has finished
+     * its work.
+     *
+     * @return the password. A copy of the internal password is created and
+     *         returned, so subsequent changes to the internal password do not
+     *         affect the result.
+     */
+    public char[] getPassword() {
+        if (inputPassword != null) {
+            char[] tmp = new char[inputPassword.length];
+            System.arraycopy(inputPassword, 0, tmp, 0, tmp.length);
+            return tmp;
+        }
+        return null;
+    }
+
+    /**
+     * Clears the password stored in this {@code PasswordCallback}.
+     */
+    public void clearPassword() {
+        if (inputPassword != null) {
+            Arrays.fill(inputPassword, '\u0000');
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/TextInputCallback.java b/src/org/apache/harmony/javax/security/auth/callback/TextInputCallback.java
new file mode 100644
index 0000000..c7de222
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/TextInputCallback.java
@@ -0,0 +1,74 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+
+
+
+public class TextInputCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = -8064222478852811804L;
+
+    private String defaultText;
+
+    private String prompt;
+
+    private String inputText;
+
+    private void setPrompt(String prompt) {
+        if (prompt == null || prompt.length() == 0) {
+            throw new IllegalArgumentException("auth.14"); //$NON-NLS-1$
+        }
+        this.prompt = prompt;
+    }
+
+    private void setDefaultText(String defaultText) {
+        if (defaultText == null || defaultText.length() == 0) {
+            throw new IllegalArgumentException("auth.15"); //$NON-NLS-1$
+        }
+        this.defaultText = defaultText;
+    }
+
+    public TextInputCallback(String prompt) {
+        super();
+        setPrompt(prompt);
+    }
+
+    public TextInputCallback(String prompt, String defaultText) {
+        super();
+        setPrompt(prompt);
+        setDefaultText(defaultText);
+    }
+
+    public String getDefaultText() {
+        return defaultText;
+    }
+
+    public String getPrompt() {
+        return prompt;
+    }
+
+    public String getText() {
+        return inputText;
+    }
+
+    public void setText(String text) {
+        this.inputText = text;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/TextOutputCallback.java b/src/org/apache/harmony/javax/security/auth/callback/TextOutputCallback.java
new file mode 100644
index 0000000..23a72fa
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/TextOutputCallback.java
@@ -0,0 +1,56 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+import java.io.Serializable;
+
+
+
+public class TextOutputCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = 1689502495511663102L;
+
+    public static final int INFORMATION = 0;
+
+    public static final int WARNING = 1;
+
+    public static final int ERROR = 2;
+
+    private String message;
+
+    private int messageType;
+
+    public TextOutputCallback(int messageType, String message) {
+        if (messageType > ERROR || messageType < INFORMATION) {
+            throw new IllegalArgumentException("auth.16"); //$NON-NLS-1$
+        }
+        if (message == null || message.length() == 0) {
+            throw new IllegalArgumentException("auth.1F"); //$NON-NLS-1$
+        }
+        this.messageType = messageType;
+        this.message = message;
+    }
+
+    public String getMessage() {
+        return message;
+    }
+
+    public int getMessageType() {
+        return messageType;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/callback/UnsupportedCallbackException.java b/src/org/apache/harmony/javax/security/auth/callback/UnsupportedCallbackException.java
new file mode 100644
index 0000000..19f6e40
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/callback/UnsupportedCallbackException.java
@@ -0,0 +1,64 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.callback;
+
+/**
+ * Thrown when a {@link CallbackHandler} does not support a particular {@link
+ * Callback}.
+ */
+public class UnsupportedCallbackException extends Exception {
+
+    private static final long serialVersionUID = -6873556327655666839L;
+
+    private Callback callback;
+
+    /**
+     * Creates a new exception instance and initializes it with just the
+     * unsupported {@code Callback}, but no error message.
+     *
+     * @param callback
+     *            the {@code Callback}
+     */
+    public UnsupportedCallbackException(Callback callback) {
+        super();
+        this.callback = callback;
+    }
+
+    /**
+     * Creates a new exception instance and initializes it with both the
+     * unsupported {@code Callback} and an error message.
+     *
+     * @param callback
+     *            the {@code Callback}
+     * @param message
+     *            the error message
+     */
+    public UnsupportedCallbackException(Callback callback, String message) {
+        super(message);
+        this.callback = callback;
+    }
+
+    /**
+     * Returns the unsupported {@code Callback} that triggered this exception.
+     *
+     * @return the {@code Callback}
+     */
+    public Callback getCallback() {
+        return callback;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/AccountException.java b/src/org/apache/harmony/javax/security/auth/login/AccountException.java
new file mode 100644
index 0000000..c86e801
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/AccountException.java
@@ -0,0 +1,31 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class AccountException extends LoginException {
+
+    private static final long serialVersionUID = -2112878680072211787L;
+
+    public AccountException() {
+        super();
+    }
+
+    public AccountException(String message) {
+        super(message);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/AccountExpiredException.java b/src/org/apache/harmony/javax/security/auth/login/AccountExpiredException.java
new file mode 100644
index 0000000..1e0ce4d
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/AccountExpiredException.java
@@ -0,0 +1,31 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class AccountExpiredException extends AccountException {
+
+    private static final long serialVersionUID = -6064064890162661560L;
+
+    public AccountExpiredException() {
+        super();
+    }
+
+    public AccountExpiredException(String message) {
+        super(message);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/AccountLockedException.java b/src/org/apache/harmony/javax/security/auth/login/AccountLockedException.java
new file mode 100644
index 0000000..47913a5
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/AccountLockedException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class AccountLockedException extends AccountException {
+
+    private static final long serialVersionUID = 8280345554014066334L;
+
+    public AccountLockedException() {
+        super();
+    }
+
+    public AccountLockedException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/AccountNotFoundException.java b/src/org/apache/harmony/javax/security/auth/login/AccountNotFoundException.java
new file mode 100644
index 0000000..8ca9b96
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/AccountNotFoundException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class AccountNotFoundException extends AccountException {
+
+    private static final long serialVersionUID = 1498349563916294614L;
+
+    public AccountNotFoundException() {
+        super();
+    }
+
+    public AccountNotFoundException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/AppConfigurationEntry.java b/src/org/apache/harmony/javax/security/auth/login/AppConfigurationEntry.java
new file mode 100644
index 0000000..2a735dc
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/AppConfigurationEntry.java
@@ -0,0 +1,95 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+import java.util.Collections;
+import java.util.Map;
+
+
+
+public class AppConfigurationEntry {
+
+    // the login module options
+    private final Map<String, ?> options;
+
+    // the control flag
+    private final AppConfigurationEntry.LoginModuleControlFlag controlFlag;
+
+    // the login module name 
+    private final String loginModuleName;
+
+    public AppConfigurationEntry(String loginModuleName,
+            AppConfigurationEntry.LoginModuleControlFlag controlFlag, Map<String, ?> options) {
+
+        if (loginModuleName == null || loginModuleName.length() == 0) {
+            throw new IllegalArgumentException("auth.26"); //$NON-NLS-1$
+        }
+
+        if (controlFlag == null) {
+            throw new IllegalArgumentException("auth.27"); //$NON-NLS-1$
+        }
+
+        if (options == null) {
+            throw new IllegalArgumentException("auth.1A"); //$NON-NLS-1$
+        }
+
+        this.loginModuleName = loginModuleName;
+        this.controlFlag = controlFlag;
+        this.options = Collections.unmodifiableMap(options);
+    }
+
+    public String getLoginModuleName() {
+        return loginModuleName;
+    }
+
+    public LoginModuleControlFlag getControlFlag() {
+        return controlFlag;
+    }
+
+    public Map<java.lang.String, ?> getOptions() {
+        return options;
+    }
+
+    public static class LoginModuleControlFlag {
+
+        // the control flag
+        private final String flag;
+
+        public static final LoginModuleControlFlag REQUIRED = new LoginModuleControlFlag(
+                "LoginModuleControlFlag: required"); //$NON-NLS-1$
+
+        public static final LoginModuleControlFlag REQUISITE = new LoginModuleControlFlag(
+                "LoginModuleControlFlag: requisite"); //$NON-NLS-1$
+
+        public static final LoginModuleControlFlag OPTIONAL = new LoginModuleControlFlag(
+                "LoginModuleControlFlag: optional"); //$NON-NLS-1$
+
+        public static final LoginModuleControlFlag SUFFICIENT = new LoginModuleControlFlag(
+                "LoginModuleControlFlag: sufficient"); //$NON-NLS-1$
+
+        // Creates the LoginModuleControlFlag object with specified a flag
+        private LoginModuleControlFlag(String flag) {
+            this.flag = flag;
+        }
+
+        @Override
+        public String toString() {
+            return flag;
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/Configuration.java b/src/org/apache/harmony/javax/security/auth/login/Configuration.java
new file mode 100644
index 0000000..74c371f
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/Configuration.java
@@ -0,0 +1,102 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+import java.security.AccessController;
+import org.apache.harmony.javax.security.auth.AuthPermission;
+
+public abstract class Configuration {
+
+    // the current configuration 
+    private static Configuration configuration;
+
+    // creates a AuthPermission object with a specify property
+    private static final AuthPermission GET_LOGIN_CONFIGURATION = new AuthPermission(
+            "getLoginConfiguration"); //$NON-NLS-1$
+
+    // creates a AuthPermission object with a specify property
+    private static final AuthPermission SET_LOGIN_CONFIGURATION = new AuthPermission(
+            "setLoginConfiguration"); //$NON-NLS-1$
+
+    // Key to security properties, defining default configuration provider.
+    private static final String LOGIN_CONFIGURATION_PROVIDER = "login.configuration.provider"; //$NON-NLS-1$
+
+    protected Configuration() {
+        super();
+    }
+
+    public static Configuration getConfiguration() {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null) {
+            sm.checkPermission(GET_LOGIN_CONFIGURATION);
+        }
+        return getAccessibleConfiguration();
+    }
+
+    /**
+     * Reads name of default configuration provider from security.properties,
+     * loads the class and instantiates the provider.<br> In case of any
+     * exception, wraps it with SecurityException and throws further.
+     */
+    private static final Configuration getDefaultProvider() {
+        return new Configuration() {
+			
+			@Override
+			public void refresh() {
+			}
+			
+			@Override
+			public AppConfigurationEntry[] getAppConfigurationEntry(
+					String applicationName) {
+				return new AppConfigurationEntry[0];
+			}
+		};
+    }
+
+    /**
+     * Shortcut accessor for friendly classes, to skip security checks.
+     * If active configuration was set to <code>null</code>, tries to load a default 
+     * provider, so this method never returns <code>null</code>. <br>
+     * This method is synchronized with setConfiguration()
+     */
+    static Configuration getAccessibleConfiguration() {
+        Configuration current = configuration;
+        if (current == null) {
+            synchronized (Configuration.class) {
+                if (configuration == null) {
+                    configuration = getDefaultProvider();
+                }
+                return configuration;
+            }
+        }
+        return current;
+    }
+
+    public static void setConfiguration(Configuration configuration) {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null) {
+            sm.checkPermission(SET_LOGIN_CONFIGURATION);
+        }
+        Configuration.configuration = configuration;
+    }
+
+    public abstract AppConfigurationEntry[] getAppConfigurationEntry(String applicationName);
+
+    public abstract void refresh();
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/CredentialException.java b/src/org/apache/harmony/javax/security/auth/login/CredentialException.java
new file mode 100644
index 0000000..e74e866
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/CredentialException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class CredentialException extends LoginException {
+
+    private static final long serialVersionUID = -4772893876810601859L;
+
+    public CredentialException() {
+        super();
+    }
+
+    public CredentialException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/CredentialExpiredException.java b/src/org/apache/harmony/javax/security/auth/login/CredentialExpiredException.java
new file mode 100644
index 0000000..3ca3ad7
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/CredentialExpiredException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class CredentialExpiredException extends CredentialException {
+
+    private static final long serialVersionUID = -5344739593859737937L;
+
+    public CredentialExpiredException() {
+        super();
+    }
+
+    public CredentialExpiredException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/CredentialNotFoundException.java b/src/org/apache/harmony/javax/security/auth/login/CredentialNotFoundException.java
new file mode 100644
index 0000000..ffd529f
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/CredentialNotFoundException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class CredentialNotFoundException extends CredentialException {
+
+    private static final long serialVersionUID = -7779934467214319475L;
+
+    public CredentialNotFoundException() {
+        super();
+    }
+
+    public CredentialNotFoundException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/FailedLoginException.java b/src/org/apache/harmony/javax/security/auth/login/FailedLoginException.java
new file mode 100644
index 0000000..f689d99
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/FailedLoginException.java
@@ -0,0 +1,32 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+public class FailedLoginException extends LoginException {
+
+    private static final long serialVersionUID = 802556922354616286L;
+
+    public FailedLoginException() {
+        super();
+    }
+
+    public FailedLoginException(String message) {
+        super(message);
+    }
+
+}
\ No newline at end of file
diff --git a/src/org/apache/harmony/javax/security/auth/login/LoginContext.java b/src/org/apache/harmony/javax/security/auth/login/LoginContext.java
new file mode 100644
index 0000000..7d46278
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/LoginContext.java
@@ -0,0 +1,548 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+import java.io.IOException;
+import java.security.AccessController;
+import java.security.AccessControlContext;
+import java.security.PrivilegedExceptionAction;
+import java.security.PrivilegedActionException;
+
+import java.security.Security;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.harmony.javax.security.auth.Subject;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.UnsupportedCallbackException;
+import org.apache.harmony.javax.security.auth.spi.LoginModule;
+import org.apache.harmony.javax.security.auth.AuthPermission;
+
+import org.apache.harmony.javax.security.auth.login.AppConfigurationEntry.LoginModuleControlFlag;
+
+
+
+public class LoginContext {
+
+    private static final String DEFAULT_CALLBACK_HANDLER_PROPERTY = "auth.login.defaultCallbackHandler"; //$NON-NLS-1$
+
+    /*
+     * Integer constants which serve as a replacement for the corresponding
+     * LoginModuleControlFlag.* constants. These integers are used later as
+     * index in the arrays - see loginImpl() and logoutImpl() methods
+     */
+    private static final int OPTIONAL = 0;
+
+    private static final int REQUIRED = 1;
+
+    private static final int REQUISITE = 2;
+
+    private static final int SUFFICIENT = 3;
+
+    // Subject to be used for this LoginContext's operations
+    private Subject subject;
+
+    /*
+     * Shows whether the subject was specified by user (true) or was created by
+     * this LoginContext itself (false).
+     */
+    private boolean userProvidedSubject;
+
+    // Shows whether we use installed or user-provided Configuration
+    private boolean userProvidedConfig;
+
+    // An user's AccessControlContext, used when user specifies 
+    private AccessControlContext userContext;
+
+    /*
+     * Either a callback handler passed by the user or a wrapper for the user's
+     * specified handler - see init() below.
+     */
+    private CallbackHandler callbackHandler;
+
+    /*
+     * An array which keeps the instantiated and init()-ialized login modules
+     * and their states
+     */
+    private Module[] modules;
+
+    // Stores a shared state
+    private Map<String, ?> sharedState;
+
+    // A context class loader used to load [mainly] LoginModules
+    private ClassLoader contextClassLoader;
+
+    // Shows overall status - whether this LoginContext was successfully logged 
+    private boolean loggedIn;
+
+    public LoginContext(String name) throws LoginException {
+        super();
+        init(name, null, null, null);
+    }
+
+    public LoginContext(String name, CallbackHandler cbHandler) throws LoginException {
+        super();
+        if (cbHandler == null) {
+            throw new LoginException("auth.34"); //$NON-NLS-1$
+        }
+        init(name, null, cbHandler, null);
+    }
+
+    public LoginContext(String name, Subject subject) throws LoginException {
+        super();
+        if (subject == null) {
+            throw new LoginException("auth.03"); //$NON-NLS-1$
+        }
+        init(name, subject, null, null);
+    }
+
+    public LoginContext(String name, Subject subject, CallbackHandler cbHandler)
+            throws LoginException {
+        super();
+        if (subject == null) {
+            throw new LoginException("auth.03"); //$NON-NLS-1$
+        }
+        if (cbHandler == null) {
+            throw new LoginException("auth.34"); //$NON-NLS-1$
+        }
+        init(name, subject, cbHandler, null);
+    }
+
+    public LoginContext(String name, Subject subject, CallbackHandler cbHandler,
+            Configuration config) throws LoginException {
+        super();
+        init(name, subject, cbHandler, config);
+    }
+
+    // Does all the machinery needed for the initialization.
+    private void init(String name, Subject subject, final CallbackHandler cbHandler,
+            Configuration config) throws LoginException {
+        userProvidedSubject = (this.subject = subject) != null;
+
+        //
+        // Set config
+        //
+        if (name == null) {
+            throw new LoginException("auth.00"); //$NON-NLS-1$
+        }
+
+        if (config == null) {
+            config = Configuration.getAccessibleConfiguration();
+        } else {
+            userProvidedConfig = true;
+        }
+
+        SecurityManager sm = System.getSecurityManager();
+
+        if (sm != null && !userProvidedConfig) {
+            sm.checkPermission(new AuthPermission("createLoginContext." + name));//$NON-NLS-1$
+        }
+
+        AppConfigurationEntry[] entries = config.getAppConfigurationEntry(name);
+        if (entries == null) {
+            if (sm != null && !userProvidedConfig) {
+                sm.checkPermission(new AuthPermission("createLoginContext.other")); //$NON-NLS-1$
+            }
+            entries = config.getAppConfigurationEntry("other"); //$NON-NLS-1$
+            if (entries == null) {
+                throw new LoginException("auth.35 " + name); //$NON-NLS-1$
+            }
+        }
+
+        modules = new Module[entries.length];
+        for (int i = 0; i < modules.length; i++) {
+            modules[i] = new Module(entries[i]);
+        }
+        //
+        // Set CallbackHandler and this.contextClassLoader
+        //
+
+        /*
+         * as some of the operations to be executed (i.e. get*ClassLoader,
+         * getProperty, class loading) are security-checked, then combine all of
+         * them into a single doPrivileged() call.
+         */
+        try {
+            AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
+                public Void run() throws Exception {
+                    // First, set the 'contextClassLoader'
+                    contextClassLoader = Thread.currentThread().getContextClassLoader();
+                    if (contextClassLoader == null) {
+                        contextClassLoader = ClassLoader.getSystemClassLoader();
+                    }
+                    // then, checks whether the cbHandler is set
+                    if (cbHandler == null) {
+                        // well, let's try to find it
+                        String klassName = Security
+                                .getProperty(DEFAULT_CALLBACK_HANDLER_PROPERTY);
+                        if (klassName == null || klassName.length() == 0) {
+                            return null;
+                        }
+                        Class<?> klass = Class.forName(klassName, true, contextClassLoader);
+                        callbackHandler = (CallbackHandler) klass.newInstance();
+                    } else {
+                        callbackHandler = cbHandler;
+                    }
+                    return null;
+                }
+            });
+        } catch (PrivilegedActionException ex) {
+            Throwable cause = ex.getCause();
+            throw (LoginException) new LoginException("auth.36").initCause(cause);//$NON-NLS-1$
+        }
+
+        if (userProvidedConfig) {
+            userContext = AccessController.getContext();
+        } else if (callbackHandler != null) {
+            userContext = AccessController.getContext();
+            callbackHandler = new ContextedCallbackHandler(callbackHandler);
+        }
+    }
+
+    public Subject getSubject() {
+        if (userProvidedSubject || loggedIn) {
+            return subject;
+        }
+        return null;
+    }
+
+    /**
+     * Warning: calling the method more than once may result in undefined
+     * behaviour if logout() method is not invoked before.
+     */
+    public void login() throws LoginException {
+        PrivilegedExceptionAction<Void> action = new PrivilegedExceptionAction<Void>() {
+            public Void run() throws LoginException {
+                loginImpl();
+                return null;
+            }
+        };
+        try {
+            if (userProvidedConfig) {
+                AccessController.doPrivileged(action, userContext);
+            } else {
+                AccessController.doPrivileged(action);
+            }
+        } catch (PrivilegedActionException ex) {
+            throw (LoginException) ex.getException();
+        }
+    }
+
+    /**
+     * The real implementation of login() method whose calls are wrapped into
+     * appropriate doPrivileged calls in login().
+     */
+    private void loginImpl() throws LoginException {
+        if (subject == null) {
+            subject = new Subject();
+        }
+
+        if (sharedState == null) {
+            sharedState = new HashMap<String, Object>();
+        }
+
+        // PHASE 1: Calling login()-s
+        Throwable firstProblem = null;
+
+        int[] logged = new int[4];
+        int[] total = new int[4];
+
+        for (Module module : modules) {
+            try {
+                // if a module fails during Class.forName(), then it breaks overall 
+                // attempt - see catch() below
+                module.create(subject, callbackHandler, sharedState);
+
+                if (module.module.login()) {
+                    ++total[module.getFlag()];
+                    ++logged[module.getFlag()];
+                    if (module.getFlag() == SUFFICIENT) {
+                        break;
+                    }
+                }
+            } catch (Throwable ex) {
+                if (firstProblem == null) {
+                    firstProblem = ex;
+                }
+                if (module.klass == null) {
+                    /*
+                     * an exception occurred during class lookup - overall
+                     * attempt must fail a little trick: increase the REQUIRED's
+                     * number - this will look like a failed REQUIRED module
+                     * later, so overall attempt will fail
+                     */
+                    ++total[REQUIRED];
+                    break;
+                }
+                ++total[module.getFlag()];
+                // something happened after the class was loaded
+                if (module.getFlag() == REQUISITE) {
+                    // ... and no need to walk down anymore
+                    break;
+                }
+            }
+        }
+        // end of PHASE1, 
+
+        // Let's decide whether we have either overall success or a total failure
+        boolean fail = true;
+
+        /*
+         * Note: 'failed[xxx]!=0' is not enough to check.
+         * 
+         * Use 'logged[xx] != total[xx]' instead. This is because some modules
+         * might not be counted as 'failed' if an exception occurred during
+         * preload()/Class.forName()-ing. But, such modules still get counted in
+         * the total[].
+         */
+
+        // if any REQ* module failed - then it's failure
+        if (logged[REQUIRED] != total[REQUIRED] || logged[REQUISITE] != total[REQUISITE]) {
+            // fail = true;
+        } else {
+            if (total[REQUIRED] == 0 && total[REQUISITE] == 0) {
+                // neither REQUIRED nor REQUISITE was configured.
+                // must have at least one SUFFICIENT or OPTIONAL
+                if (logged[OPTIONAL] != 0 || logged[SUFFICIENT] != 0) {
+                    fail = false;
+                }
+                //else { fail = true; }
+            } else {
+                fail = false;
+            }
+        }
+
+        int commited[] = new int[4];
+        // clear it
+        total[0] = total[1] = total[2] = total[3] = 0;
+        if (!fail) {
+            // PHASE 2: 
+
+            for (Module module : modules) {
+                if (module.klass != null) {
+                    ++total[module.getFlag()];
+                    try {
+                        module.module.commit();
+                        ++commited[module.getFlag()];
+                    } catch (Throwable ex) {
+                        if (firstProblem == null) {
+                            firstProblem = ex;
+                        }
+                    }
+                }
+            }
+        }
+
+        // need to decide once again
+        fail = true;
+        if (commited[REQUIRED] != total[REQUIRED] || commited[REQUISITE] != total[REQUISITE]) {
+            //fail = true;
+        } else {
+            if (total[REQUIRED] == 0 && total[REQUISITE] == 0) {
+                /*
+                 * neither REQUIRED nor REQUISITE was configured. must have at
+                 * least one SUFFICIENT or OPTIONAL
+                 */
+                if (commited[OPTIONAL] != 0 || commited[SUFFICIENT] != 0) {
+                    fail = false;
+                } else {
+                    //fail = true;
+                }
+            } else {
+                fail = false;
+            }
+        }
+
+        if (fail) {
+            // either login() or commit() failed. aborting...
+
+            for (Module module : modules) {
+                try {
+                    module.module.abort();
+                } catch ( /*LoginException*/Throwable ex) {
+                    if (firstProblem == null) {
+                        firstProblem = ex;
+                    }
+                }
+            }
+            if (firstProblem instanceof PrivilegedActionException
+                    && firstProblem.getCause() != null) {
+                firstProblem = firstProblem.getCause();
+            }
+            if (firstProblem instanceof LoginException) {
+                throw (LoginException) firstProblem;
+            }
+            throw (LoginException) new LoginException("auth.37").initCause(firstProblem); //$NON-NLS-1$
+        }
+        loggedIn = true;
+    }
+
+    public void logout() throws LoginException {
+        PrivilegedExceptionAction<Void> action = new PrivilegedExceptionAction<Void>() {
+            public Void run() throws LoginException {
+                logoutImpl();
+                return null;
+            }
+        };
+        try {
+            if (userProvidedConfig) {
+                AccessController.doPrivileged(action, userContext);
+            } else {
+                AccessController.doPrivileged(action);
+            }
+        } catch (PrivilegedActionException ex) {
+            throw (LoginException) ex.getException();
+        }
+    }
+
+    /**
+     * The real implementation of logout() method whose calls are wrapped into
+     * appropriate doPrivileged calls in logout().
+     */
+    private void logoutImpl() throws LoginException {
+        if (subject == null) {
+            throw new LoginException("auth.38"); //$NON-NLS-1$
+        }
+        loggedIn = false;
+        Throwable firstProblem = null;
+        int total = 0;
+        for (Module module : modules) {
+            try {
+                module.module.logout();
+                ++total;
+            } catch (Throwable ex) {
+                if (firstProblem == null) {
+                    firstProblem = ex;
+                }
+            }
+        }
+        if (firstProblem != null || total == 0) {
+            if (firstProblem instanceof PrivilegedActionException
+                    && firstProblem.getCause() != null) {
+                firstProblem = firstProblem.getCause();
+            }
+            if (firstProblem instanceof LoginException) {
+                throw (LoginException) firstProblem;
+            }
+            throw (LoginException) new LoginException("auth.37").initCause(firstProblem); //$NON-NLS-1$
+        }
+    }
+
+    /**
+     * <p>A class that servers as a wrapper for the CallbackHandler when we use
+     * installed Configuration, but not a passed one. See API docs on the
+     * LoginContext.</p>
+     * 
+     * <p>Simply invokes the given handler with the given AccessControlContext.</p>
+     */
+    private class ContextedCallbackHandler implements CallbackHandler {
+        private final CallbackHandler hiddenHandlerRef;
+
+        ContextedCallbackHandler(CallbackHandler handler) {
+            super();
+            this.hiddenHandlerRef = handler;
+        }
+
+        public void handle(final Callback[] callbacks) throws IOException,
+                UnsupportedCallbackException {
+            try {
+                AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
+                    public Void run() throws IOException, UnsupportedCallbackException {
+                        hiddenHandlerRef.handle(callbacks);
+                        return null;
+                    }
+                }, userContext);
+            } catch (PrivilegedActionException ex) {
+                if (ex.getCause() instanceof UnsupportedCallbackException) {
+                    throw (UnsupportedCallbackException) ex.getCause();
+                }
+                throw (IOException) ex.getCause();
+            }
+        }
+    }
+
+    /** 
+     * A private class that stores an instantiated LoginModule.
+     */
+    private final class Module {
+
+        // An initial info about the module to be used
+        AppConfigurationEntry entry;
+
+        // A mapping of LoginModuleControlFlag onto a simple int constant
+        int flag;
+
+        // The LoginModule itself 
+        LoginModule module;
+
+        // A class of the module
+        Class<?> klass;
+
+        Module(AppConfigurationEntry entry) {
+            this.entry = entry;
+            LoginModuleControlFlag flg = entry.getControlFlag();
+            if (flg == LoginModuleControlFlag.OPTIONAL) {
+                flag = OPTIONAL;
+            } else if (flg == LoginModuleControlFlag.REQUISITE) {
+                flag = REQUISITE;
+            } else if (flg == LoginModuleControlFlag.SUFFICIENT) {
+                flag = SUFFICIENT;
+            } else {
+                flag = REQUIRED;
+                //if(flg!=LoginModuleControlFlag.REQUIRED) throw new Error()
+            }
+        }
+
+        int getFlag() {
+            return flag;
+        }
+
+        /**
+         * Loads class of the LoginModule, instantiates it and then calls
+         * initialize().
+         */
+        void create(Subject subject, CallbackHandler callbackHandler, Map<String, ?> sharedState)
+                throws LoginException {
+            String klassName = entry.getLoginModuleName();
+            if (klass == null) {
+                try {
+                    klass = Class.forName(klassName, false, contextClassLoader);
+                } catch (ClassNotFoundException ex) {
+                    throw (LoginException) new LoginException(
+                            "auth.39 " + klassName).initCause(ex); //$NON-NLS-1$
+                }
+            }
+
+            if (module == null) {
+                try {
+                    module = (LoginModule) klass.newInstance();
+                } catch (IllegalAccessException ex) {
+                    throw (LoginException) new LoginException(
+                            "auth.3A " + klassName) //$NON-NLS-1$
+                            .initCause(ex);
+                } catch (InstantiationException ex) {
+                    throw (LoginException) new LoginException(
+                            "auth.3A" + klassName) //$NON-NLS-1$
+                            .initCause(ex);
+                }
+                module.initialize(subject, callbackHandler, sharedState, entry.getOptions());
+            }
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/auth/login/LoginException.java b/src/org/apache/harmony/javax/security/auth/login/LoginException.java
new file mode 100644
index 0000000..e9ea566
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/login/LoginException.java
@@ -0,0 +1,45 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.login;
+
+import java.security.GeneralSecurityException;
+
+/**
+ * Base class for exceptions that are thrown when a login error occurs.
+ */
+public class LoginException extends GeneralSecurityException {
+
+    private static final long serialVersionUID = -4679091624035232488L;
+
+    /**
+     * Creates a new exception instance and initializes it with default values.
+     */
+    public LoginException() {
+        super();
+    }
+
+    /**
+     * Creates a new exception instance and initializes it with a given message.
+     *
+     * @param message the error message
+     */
+    public LoginException(String message) {
+        super(message);
+    }
+
+}
diff --git a/src/org/apache/harmony/javax/security/auth/spi/LoginModule.java b/src/org/apache/harmony/javax/security/auth/spi/LoginModule.java
new file mode 100644
index 0000000..3ed9eb2
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/auth/spi/LoginModule.java
@@ -0,0 +1,38 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.auth.spi;
+
+import java.util.Map;
+
+import org.apache.harmony.javax.security.auth.Subject;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.login.LoginException;
+
+public interface LoginModule {
+
+    void initialize(Subject subject, CallbackHandler callbackHandler,
+            Map<String, ?> sharedState, Map<String, ?> options);
+
+    boolean login() throws LoginException;
+
+    boolean commit() throws LoginException;
+
+    boolean abort() throws LoginException;
+
+    boolean logout() throws LoginException;
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/AuthenticationException.java b/src/org/apache/harmony/javax/security/sasl/AuthenticationException.java
new file mode 100644
index 0000000..38703ef
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/AuthenticationException.java
@@ -0,0 +1,35 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+public class AuthenticationException extends SaslException {
+
+    private static final long serialVersionUID = -3579708765071815007L;
+
+    public AuthenticationException() {
+        super();
+    }
+
+    public AuthenticationException(String detail) {
+        super(detail);
+    }
+
+    public AuthenticationException(String detail, Throwable ex) {
+        super(detail, ex);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/AuthorizeCallback.java b/src/org/apache/harmony/javax/security/sasl/AuthorizeCallback.java
new file mode 100644
index 0000000..2ba90a2
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/AuthorizeCallback.java
@@ -0,0 +1,79 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import java.io.Serializable;
+import org.apache.harmony.javax.security.auth.callback.Callback;
+
+public class AuthorizeCallback implements Callback, Serializable {
+
+    private static final long serialVersionUID = -2353344186490470805L;
+
+    /**
+     * Serialized field for storing authenticationID.
+     */
+    private final String authenticationID;
+
+    /**
+     * Serialized field for storing authorizationID.
+     */
+    private final String authorizationID;
+
+    /**
+     * Serialized field for storing authorizedID.
+     */
+    private String authorizedID;
+
+    /**
+     * Store authorized Serialized field.
+     */
+    private boolean authorized;
+
+    public AuthorizeCallback(String authnID, String authzID) {
+        super();
+        authenticationID = authnID;
+        authorizationID = authzID;
+        authorizedID = authzID;
+    }
+
+    public String getAuthenticationID() {
+        return authenticationID;
+    }
+
+    public String getAuthorizationID() {
+        return authorizationID;
+    }
+
+    public String getAuthorizedID() {
+        return (authorized ? authorizedID : null);
+    }
+
+    public boolean isAuthorized() {
+        return authorized;
+    }
+
+    public void setAuthorized(boolean ok) {
+        authorized = ok;
+    }
+
+    public void setAuthorizedID(String id) {
+        if (id != null) {
+            authorizedID = id;
+        }
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/RealmCallback.java b/src/org/apache/harmony/javax/security/sasl/RealmCallback.java
new file mode 100644
index 0000000..65b5d15
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/RealmCallback.java
@@ -0,0 +1,33 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.TextInputCallback;
+
+public class RealmCallback extends TextInputCallback {
+
+    private static final long serialVersionUID = -4342673378785456908L;
+
+    public RealmCallback(String prompt) {
+        super(prompt);
+    }
+
+    public RealmCallback(String prompt, String defaultRealmInfo) {
+        super(prompt, defaultRealmInfo);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/RealmChoiceCallback.java b/src/org/apache/harmony/javax/security/sasl/RealmChoiceCallback.java
new file mode 100644
index 0000000..079ea07
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/RealmChoiceCallback.java
@@ -0,0 +1,30 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.ChoiceCallback;
+
+public class RealmChoiceCallback extends ChoiceCallback {
+
+    private static final long serialVersionUID = -8588141348846281332L;
+
+    public RealmChoiceCallback(String prompt, String[] choices, int defaultChoice,
+            boolean multiple) {
+        super(prompt, choices, defaultChoice, multiple);
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/Sasl.java b/src/org/apache/harmony/javax/security/sasl/Sasl.java
new file mode 100644
index 0000000..4d827f8
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/Sasl.java
@@ -0,0 +1,204 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import java.security.Provider;
+import java.security.Security;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+
+
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Enumeration;
+import java.util.Map;
+import java.util.HashSet;
+import java.util.Iterator;
+
+public class Sasl {
+    // SaslClientFactory service name
+    private static final String CLIENTFACTORYSRV = "SaslClientFactory"; //$NON-NLS-1$
+
+    // SaslServerFactory service name
+    private static final String SERVERFACTORYSRV = "SaslServerFactory"; //$NON-NLS-1$
+
+    public static final String POLICY_NOPLAINTEXT = "javax.security.sasl.policy.noplaintext"; //$NON-NLS-1$
+
+    public static final String POLICY_NOACTIVE = "javax.security.sasl.policy.noactive"; //$NON-NLS-1$
+
+    public static final String POLICY_NODICTIONARY = "javax.security.sasl.policy.nodictionary"; //$NON-NLS-1$
+
+    public static final String POLICY_NOANONYMOUS = "javax.security.sasl.policy.noanonymous"; //$NON-NLS-1$
+
+    public static final String POLICY_FORWARD_SECRECY = "javax.security.sasl.policy.forward"; //$NON-NLS-1$
+
+    public static final String POLICY_PASS_CREDENTIALS = "javax.security.sasl.policy.credentials"; //$NON-NLS-1$
+
+    public static final String MAX_BUFFER = "javax.security.sasl.maxbuffer"; //$NON-NLS-1$
+
+    public static final String RAW_SEND_SIZE = "javax.security.sasl.rawsendsize"; //$NON-NLS-1$
+
+    public static final String REUSE = "javax.security.sasl.reuse"; //$NON-NLS-1$
+
+    public static final String QOP = "javax.security.sasl.qop"; //$NON-NLS-1$
+
+    public static final String STRENGTH = "javax.security.sasl.strength"; //$NON-NLS-1$
+
+    public static final String SERVER_AUTH = "javax.security.sasl.server.authentication"; //$NON-NLS-1$
+
+    // Default public constructor is overridden
+    private Sasl() {
+        super();
+    }
+
+    // Forms new instance of factory
+    private static Object newInstance(String factoryName, Provider prv) throws SaslException {
+        String msg = "auth.31"; //$NON-NLS-1$
+        Object factory;
+        ClassLoader cl = prv.getClass().getClassLoader();
+        if (cl == null) {
+            cl = ClassLoader.getSystemClassLoader();
+        }
+        try {
+            factory = (Class.forName(factoryName, true, cl)).newInstance();
+            return factory;
+        } catch (IllegalAccessException e) {
+            throw new SaslException(msg + factoryName, e);
+        } catch (ClassNotFoundException e) {
+            throw new SaslException(msg + factoryName, e);
+        } catch (InstantiationException e) {
+            throw new SaslException(msg + factoryName, e);
+        }
+    }
+
+    /**
+     * This method forms the list of SaslClient/SaslServer factories which are
+     * implemented in used providers
+     */
+    private static Collection<?> findFactories(String service) {
+        HashSet<Object> fact = new HashSet<Object>();
+        Provider[] pp = Security.getProviders();
+        if ((pp == null) || (pp.length == 0)) {
+            return fact;
+        }
+        HashSet<String> props = new HashSet<String>();
+        for (int i = 0; i < pp.length; i++) {
+            String prName = pp[i].getName();
+            Enumeration<Object> keys = pp[i].keys();
+            while (keys.hasMoreElements()) {
+                String s = (String) keys.nextElement();
+                if (s.startsWith(service)) {
+                    String prop = pp[i].getProperty(s);
+                    try {
+                        if (props.add(prName.concat(prop))) {
+                            fact.add(newInstance(prop, pp[i]));
+                        }
+                    } catch (SaslException e) {
+                        // ignore this factory
+                        e.printStackTrace();
+                    }
+                }
+            }
+        }
+        return fact;
+    }
+
+    @SuppressWarnings("unchecked")
+    public static Enumeration<SaslClientFactory> getSaslClientFactories() {
+        Collection<SaslClientFactory> res = (Collection<SaslClientFactory>) findFactories(CLIENTFACTORYSRV);
+        return Collections.enumeration(res);
+
+    }
+
+    @SuppressWarnings("unchecked")
+    public static Enumeration<SaslServerFactory> getSaslServerFactories() {
+        Collection<SaslServerFactory> res = (Collection<SaslServerFactory>) findFactories(SERVERFACTORYSRV);
+        return Collections.enumeration(res);
+    }
+
+    public static SaslServer createSaslServer(String mechanism, String protocol,
+            String serverName, Map<String, ?> prop, CallbackHandler cbh) throws SaslException {
+        if (mechanism == null) {
+            throw new NullPointerException("auth.32"); //$NON-NLS-1$
+        }
+        Collection<?> res = findFactories(SERVERFACTORYSRV);
+        if (res.isEmpty()) {
+            return null;
+        }
+
+        Iterator<?> iter = res.iterator();
+        while (iter.hasNext()) {
+            SaslServerFactory fact = (SaslServerFactory) iter.next();
+            String[] mech = fact.getMechanismNames(null);
+            boolean is = false;
+            if (mech != null) {
+                for (int j = 0; j < mech.length; j++) {
+                    if (mech[j].equals(mechanism)) {
+                        is = true;
+                        break;
+                    }
+                }
+            }
+            if (is) {
+                SaslServer saslS = fact.createSaslServer(mechanism, protocol, serverName, prop,
+                        cbh);
+                if (saslS != null) {
+                    return saslS;
+                }
+            }
+        }
+        return null;
+    }
+
+    public static SaslClient createSaslClient(String[] mechanisms, String authanticationID,
+            String protocol, String serverName, Map<String, ?> prop, CallbackHandler cbh)
+            throws SaslException {
+        if (mechanisms == null) {
+            throw new NullPointerException("auth.33"); //$NON-NLS-1$
+        }
+        Collection<?> res = findFactories(CLIENTFACTORYSRV);
+        if (res.isEmpty()) {
+            return null;
+        }
+
+        Iterator<?> iter = res.iterator();
+        while (iter.hasNext()) {
+            SaslClientFactory fact = (SaslClientFactory) iter.next();
+            String[] mech = fact.getMechanismNames(null);
+            boolean is = false;
+            if (mech != null) {
+                for (int j = 0; j < mech.length; j++) {
+                    for (int n = 0; n < mechanisms.length; n++) {
+                        if (mech[j].equals(mechanisms[n])) {
+                            is = true;
+                            break;
+                        }
+                    }
+                }
+            }
+            if (is) {
+                SaslClient saslC = fact.createSaslClient(mechanisms, authanticationID,
+                        protocol, serverName, prop, cbh);
+                if (saslC != null) {
+                    return saslC;
+                }
+            }
+        }
+        return null;
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/SaslClient.java b/src/org/apache/harmony/javax/security/sasl/SaslClient.java
new file mode 100644
index 0000000..e07ff53
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/SaslClient.java
@@ -0,0 +1,37 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+public interface SaslClient {
+
+    void dispose() throws SaslException;
+
+    byte[] evaluateChallenge(byte[] challenge) throws SaslException;
+
+    String getMechanismName();
+
+    Object getNegotiatedProperty(String propName);
+
+    boolean hasInitialResponse();
+
+    boolean isComplete();
+
+    byte[] unwrap(byte[] incoming, int offset, int len) throws SaslException;
+
+    byte[] wrap(byte[] outgoing, int offset, int len) throws SaslException;
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/SaslClientFactory.java b/src/org/apache/harmony/javax/security/sasl/SaslClientFactory.java
new file mode 100644
index 0000000..e567ed3
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/SaslClientFactory.java
@@ -0,0 +1,30 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import java.util.Map;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+public interface SaslClientFactory {
+
+    SaslClient createSaslClient(String[] mechanisms, String authorizationId, String protocol,
+            String serverName, Map<String, ?> props, CallbackHandler cbh) throws SaslException;
+
+    String[] getMechanismNames(Map<String, ?> props);
+
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/SaslException.java b/src/org/apache/harmony/javax/security/sasl/SaslException.java
new file mode 100644
index 0000000..1ab7b12
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/SaslException.java
@@ -0,0 +1,69 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import java.io.IOException;
+
+public class SaslException extends IOException {
+
+    private static final long serialVersionUID = 4579784287983423626L;
+
+    /**
+     * Serialized field for storing initial cause
+     */
+    private Throwable _exception;
+
+    public SaslException() {
+        super();
+    }
+
+    public SaslException(String detail) {
+        super(detail);
+    }
+
+    public SaslException(String detail, Throwable ex) {
+        super(detail);
+        if (ex != null) {
+            super.initCause(ex);
+            _exception = ex;
+        }
+    }
+
+    @Override
+    public Throwable getCause() {
+        return _exception;
+    }
+
+    @Override
+    public Throwable initCause(Throwable cause) {
+        super.initCause(cause);
+        _exception = cause;
+        return this;
+    }
+
+    @Override
+    public String toString() {
+        if (_exception == null) {
+            return super.toString();
+        }
+        StringBuilder sb = new StringBuilder(super.toString());
+        sb.append(", caused by: "); //$NON-NLS-1$
+        sb.append(_exception.toString());
+        return sb.toString();
+    }
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/SaslServer.java b/src/org/apache/harmony/javax/security/sasl/SaslServer.java
new file mode 100644
index 0000000..f057a4b
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/SaslServer.java
@@ -0,0 +1,37 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+public interface SaslServer {
+
+    void dispose() throws SaslException;
+
+    byte[] evaluateResponse(byte[] response) throws SaslException;
+
+    String getAuthorizationID();
+
+    String getMechanismName();
+
+    Object getNegotiatedProperty(String propName);
+
+    boolean isComplete();
+
+    byte[] unwrap(byte[] incoming, int offset, int len) throws SaslException;
+
+    byte[] wrap(byte[] outgoing, int offset, int len) throws SaslException;
+}
diff --git a/src/org/apache/harmony/javax/security/sasl/SaslServerFactory.java b/src/org/apache/harmony/javax/security/sasl/SaslServerFactory.java
new file mode 100644
index 0000000..d59530e
--- /dev/null
+++ b/src/org/apache/harmony/javax/security/sasl/SaslServerFactory.java
@@ -0,0 +1,30 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one or more
+ *  contributor license agreements.  See the NOTICE file distributed with
+ *  this work for additional information regarding copyright ownership.
+ *  The ASF licenses this file to You under the Apache License, Version 2.0
+ *  (the "License"); you may not use this file except in compliance with
+ *  the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.harmony.javax.security.sasl;
+
+import java.util.Map;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+public interface SaslServerFactory {
+
+    SaslServer createSaslServer(String mechanisms, String protocol, String serverName,
+            Map<String, ?> props, CallbackHandler cbh) throws SaslException;
+
+    String[] getMechanismNames(Map<String, ?> props);
+
+}
diff --git a/src/org/apache/qpid/management/common/sasl/CRAMMD5HashedSaslClientFactory.java b/src/org/apache/qpid/management/common/sasl/CRAMMD5HashedSaslClientFactory.java
new file mode 100644
index 0000000..5c33e40
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/CRAMMD5HashedSaslClientFactory.java
@@ -0,0 +1,59 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import de.measite.smack.Sasl;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslClientFactory;
+import org.apache.harmony.javax.security.sasl.SaslException;
+import java.util.Map;
+
+public class CRAMMD5HashedSaslClientFactory implements SaslClientFactory
+{
+    /** The name of this mechanism */
+    public static final String MECHANISM = "CRAM-MD5-HASHED";
+
+    public SaslClient createSaslClient(String[] mechanisms, String authorizationId, String protocol,
+                                       String serverName, Map<String, ?> props, CallbackHandler cbh)
+    throws SaslException
+    {
+        for (int i = 0; i < mechanisms.length; i++)
+        {
+            if (mechanisms[i].equals(MECHANISM))
+            {
+                if (cbh == null)
+                {
+                    throw new SaslException("CallbackHandler must not be null");
+                }
+
+                String[] mechs = {"CRAM-MD5"};
+                return Sasl.createSaslClient(mechs, authorizationId, protocol, serverName, props, cbh);
+            }
+        }
+        return null;
+    }
+
+    public String[] getMechanismNames(Map props)
+    { 
+        return new String[]{MECHANISM};
+    }
+}
diff --git a/src/org/apache/qpid/management/common/sasl/ClientSaslFactory.java b/src/org/apache/qpid/management/common/sasl/ClientSaslFactory.java
new file mode 100644
index 0000000..19162d8
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/ClientSaslFactory.java
@@ -0,0 +1,53 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslClientFactory;
+import org.apache.harmony.javax.security.sasl.SaslException;
+import java.util.Map;
+
+public class ClientSaslFactory implements SaslClientFactory
+{
+    public SaslClient createSaslClient(String[] mechs, String authorizationId, String protocol,
+                                       String serverName, Map props, CallbackHandler cbh)
+    throws SaslException 
+    {
+        for (int i = 0; i < mechs.length; i++)
+        {
+            if (mechs[i].equals("PLAIN"))
+            {
+                return new PlainSaslClient(authorizationId, cbh);
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Simple-minded implementation that ignores props
+     */
+    public String[] getMechanismNames(Map props)
+    {
+        return new String[]{"PLAIN"};
+    }
+
+}
diff --git a/src/org/apache/qpid/management/common/sasl/Constants.java b/src/org/apache/qpid/management/common/sasl/Constants.java
new file mode 100644
index 0000000..31010ba
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/Constants.java
@@ -0,0 +1,33 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+
+package org.apache.qpid.management.common.sasl;
+
+public class Constants
+{
+
+    public final static String MECH_CRAMMD5 = "CRAM-MD5";
+    public final static String MECH_PLAIN = "PLAIN";
+    public final static String SASL_CRAMMD5 = "SASL/CRAM-MD5";
+    public final static String SASL_PLAIN = "SASL/PLAIN";
+
+}
+
diff --git a/src/org/apache/qpid/management/common/sasl/JCAProvider.java b/src/org/apache/qpid/management/common/sasl/JCAProvider.java
new file mode 100644
index 0000000..5793dae
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/JCAProvider.java
@@ -0,0 +1,55 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.sasl.SaslClientFactory;
+import java.security.Provider;
+import java.util.Map;
+
+public class JCAProvider extends Provider
+{
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Creates the security provider with a map from SASL mechanisms to implementing factories.
+     *
+     * @param providerMap The map from SASL mechanims to implementing factory classes.
+     */
+    public JCAProvider(Map<String, Class<? extends SaslClientFactory>> providerMap)
+    {
+        super("AMQSASLProvider", 1.0, "A JCA provider that registers all "
+              + "AMQ SASL providers that want to be registered");
+        register(providerMap);
+    }
+
+    /**
+     * Registers client factory classes for a map of mechanism names to client factory classes.
+     *
+     * @param providerMap The map from SASL mechanims to implementing factory classes.
+     */
+    private void register(Map<String, Class<? extends SaslClientFactory>> providerMap)
+    {
+        for (Map.Entry<String, Class<? extends SaslClientFactory>> me : providerMap.entrySet())
+        {
+            put("SaslClientFactory." + me.getKey(), me.getValue().getName());
+        }
+    }
+}
diff --git a/src/org/apache/qpid/management/common/sasl/PlainSaslClient.java b/src/org/apache/qpid/management/common/sasl/PlainSaslClient.java
new file mode 100644
index 0000000..99a1d43
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/PlainSaslClient.java
@@ -0,0 +1,210 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.NameCallback;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+import org.apache.harmony.javax.security.auth.callback.UnsupportedCallbackException;
+import de.measite.smack.Sasl;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslException;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+
+public class PlainSaslClient implements SaslClient
+{
+
+    private boolean completed;
+    private CallbackHandler cbh;
+    private String authorizationID;
+    private String authenticationID;
+    private byte password[];
+    private static byte SEPARATOR = 0;
+    
+    public PlainSaslClient(String authorizationID, CallbackHandler cbh) throws SaslException
+    {
+        completed = false;
+        this.cbh = cbh;
+        Object[] userInfo = getUserInfo();
+        this.authorizationID = authorizationID;
+        this.authenticationID = (String) userInfo[0];
+        this.password = (byte[]) userInfo[1];
+        if (authenticationID == null || password == null)
+        {
+            throw new SaslException("PLAIN: authenticationID and password must be specified");
+        }
+    }
+
+    public byte[] evaluateChallenge(byte[] challenge) throws SaslException
+    {
+        if (completed)
+        {
+            throw new IllegalStateException("PLAIN: authentication already " +
+            "completed");
+        }
+        completed = true;
+        try 
+        {
+            byte authzid[] =
+                authorizationID == null ? null : authorizationID.getBytes("UTF8");
+            byte authnid[] = authenticationID.getBytes("UTF8");
+            byte response[] =
+                new byte[
+                         password.length +
+                         authnid.length +
+                         2 + // SEPARATOR
+                         (authzid != null ? authzid.length : 0)
+                         ];
+            int size = 0;
+            if (authzid != null) {
+                System.arraycopy(authzid, 0, response, 0, authzid.length);
+                size = authzid.length;
+            }
+            response[size++] = SEPARATOR;
+            System.arraycopy(authnid, 0, response, size, authnid.length);
+            size += authnid.length;
+            response[size++] = SEPARATOR;
+            System.arraycopy(password, 0, response, size, password.length);
+            clearPassword();
+            return response;
+        } catch (UnsupportedEncodingException e) {
+            throw new SaslException("PLAIN: Cannot get UTF-8 encoding of ids",
+                    e);
+        }
+    }
+
+    public String getMechanismName()
+    {
+        return "PLAIN";
+    }
+
+    public boolean hasInitialResponse()
+    {
+        return true;
+    }
+
+    public boolean isComplete()
+    {
+        return completed;
+    }
+
+    public byte[] unwrap(byte[] incoming, int offset, int len) throws SaslException
+    {
+        if (completed) {
+            throw new IllegalStateException("PLAIN: this mechanism supports " +
+            "neither integrity nor privacy");
+        } else {
+            throw new IllegalStateException("PLAIN: authentication not " +
+            "completed");
+        }
+    }
+
+    public byte[] wrap(byte[] outgoing, int offset, int len) throws SaslException
+    {
+        if (completed)
+        {
+            throw new IllegalStateException("PLAIN: this mechanism supports " +
+            "neither integrity nor privacy");
+        }
+        else
+        {
+            throw new IllegalStateException("PLAIN: authentication not " +
+            "completed");
+        }
+    }
+
+    public Object getNegotiatedProperty(String propName)
+    {
+        if (completed)
+        {
+            if (propName.equals(Sasl.QOP))
+            {
+                return "auth";
+            }
+            else
+            {
+                return null;
+            }
+        }
+        else 
+        {
+            throw new IllegalStateException("PLAIN: authentication not " +
+            "completed");
+        }
+    }
+
+    private void clearPassword()
+    {
+        if (password != null)
+        {
+            for (int i = 0 ; i < password.length ; i++)
+            {
+                password[i] = 0;
+            }
+            password = null;
+        }
+    }
+
+    public void dispose() throws SaslException
+    {
+        clearPassword();
+    }
+
+    protected void finalize()
+    {
+        clearPassword();
+    }
+
+    private Object[] getUserInfo() throws SaslException
+    {
+        try
+        {
+            final String userPrompt = "PLAIN authentication id: ";
+            final String pwPrompt = "PLAIN password: ";
+            NameCallback nameCb = new NameCallback(userPrompt);
+            PasswordCallback passwordCb = new PasswordCallback(pwPrompt, false);
+            cbh.handle(new Callback[] { nameCb, passwordCb });
+            String userid = nameCb.getName();
+            char pwchars[] = passwordCb.getPassword();
+            byte pwbytes[];
+            if (pwchars != null)
+            {
+                pwbytes = (new String(pwchars)).getBytes("UTF8");
+                passwordCb.clearPassword();
+            }
+            else 
+            {
+                pwbytes = null;
+            }
+            return (new Object[] { userid, pwbytes });
+        } 
+        catch (IOException e)
+        {
+            throw new SaslException("Cannot get password", e);
+        } 
+        catch (UnsupportedCallbackException e)
+        {
+            throw new SaslException("Cannot get userid/password", e);
+        }
+    }
+}
diff --git a/src/org/apache/qpid/management/common/sasl/SaslProvider.java b/src/org/apache/qpid/management/common/sasl/SaslProvider.java
new file mode 100644
index 0000000..1eb44e3
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/SaslProvider.java
@@ -0,0 +1,35 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import java.security.Provider;
+
+public class SaslProvider extends Provider
+{
+    private static final long serialVersionUID = -6978096016899676466L;
+
+    public SaslProvider()
+    {
+        super("SaslClientFactory", 1.0, "SASL PLAIN CLIENT MECHANISM");
+        put("SaslClientFactory.PLAIN", "ClientSaslFactory");
+    }
+
+}
diff --git a/src/org/apache/qpid/management/common/sasl/UserPasswordCallbackHandler.java b/src/org/apache/qpid/management/common/sasl/UserPasswordCallbackHandler.java
new file mode 100644
index 0000000..a7886cf
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/UserPasswordCallbackHandler.java
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.NameCallback;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+import org.apache.harmony.javax.security.auth.callback.UnsupportedCallbackException;
+import java.io.IOException;
+
+public class UserPasswordCallbackHandler implements CallbackHandler
+{
+    private String user;
+    private char[] pwchars;
+    
+    public UserPasswordCallbackHandler(String user, String password)
+    {
+        this.user = user;
+        this.pwchars = password.toCharArray();
+    }
+
+    public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException
+    {
+        for (int i = 0; i < callbacks.length; i++)
+        {
+            if (callbacks[i] instanceof NameCallback)
+            {
+                NameCallback ncb = (NameCallback) callbacks[i];
+                ncb.setName(user);
+            } 
+            else if (callbacks[i] instanceof PasswordCallback)
+            {
+                PasswordCallback pcb = (PasswordCallback) callbacks[i];
+                pcb.setPassword(pwchars);
+            } 
+            else
+            {
+                throw new UnsupportedCallbackException(callbacks[i]);
+            }
+        }
+    }
+
+    private void clearPassword()
+    {
+        if (pwchars != null) 
+        {
+            for (int i = 0 ; i < pwchars.length ; i++)
+            {
+                pwchars[i] = 0;
+            }
+            pwchars = null;
+        }
+    }
+
+    protected void finalize()
+    {
+        clearPassword();
+    }
+}
diff --git a/src/org/apache/qpid/management/common/sasl/UsernameHashedPasswordCallbackHandler.java b/src/org/apache/qpid/management/common/sasl/UsernameHashedPasswordCallbackHandler.java
new file mode 100644
index 0000000..54d7374
--- /dev/null
+++ b/src/org/apache/qpid/management/common/sasl/UsernameHashedPasswordCallbackHandler.java
@@ -0,0 +1,107 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+package org.apache.qpid.management.common.sasl;
+
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.NameCallback;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+import org.apache.harmony.javax.security.auth.callback.UnsupportedCallbackException;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+
+
+public class UsernameHashedPasswordCallbackHandler implements CallbackHandler
+{
+    private String user;
+    private char[] pwchars;
+    
+    public UsernameHashedPasswordCallbackHandler(String user, String password) throws Exception
+    {
+        this.user = user;
+        this.pwchars = getHash(password);
+    }
+
+    public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException
+    {
+        for (int i = 0; i < callbacks.length; i++)
+        {
+            if (callbacks[i] instanceof NameCallback)
+            {
+                NameCallback ncb = (NameCallback) callbacks[i];
+                ncb.setName(user);
+            } 
+            else if (callbacks[i] instanceof PasswordCallback)
+            {
+                PasswordCallback pcb = (PasswordCallback) callbacks[i];
+                pcb.setPassword(pwchars);
+            } 
+            else
+            {
+                throw new UnsupportedCallbackException(callbacks[i]);
+            }
+        }
+    }
+
+    
+    private void clearPassword()
+    {
+        if (pwchars != null) 
+        {
+            for (int i = 0 ; i < pwchars.length ; i++)
+            {
+                pwchars[i] = 0;
+            }
+            pwchars = null;
+        }
+    }
+
+    protected void finalize()
+    {
+        clearPassword();
+    }
+    
+    public static char[] getHash(String text) throws NoSuchAlgorithmException, UnsupportedEncodingException
+    {
+        byte[] data = text.getBytes("utf-8");
+
+        MessageDigest md = MessageDigest.getInstance("MD5");
+
+        for (byte b : data)
+        {
+            md.update(b);
+        }
+
+        byte[] digest = md.digest();
+
+        char[] hash = new char[digest.length ];
+
+        int index = 0;
+        for (byte b : digest)
+        {            
+            hash[index++] = (char) b;
+        }
+
+        return hash;
+    }
+}
diff --git a/src/org/jivesoftware/smack/AbstractConnectionListener.java b/src/org/jivesoftware/smack/AbstractConnectionListener.java
new file mode 100644
index 0000000..69acf90
--- /dev/null
+++ b/src/org/jivesoftware/smack/AbstractConnectionListener.java
@@ -0,0 +1,46 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack;
+
+/**
+ * The AbstractConnectionListener class provides an empty implementation for all
+ * methods defined by the {@link ConnectionListener} interface. This is a
+ * convenience class which should be used in case you do not need to implement
+ * all methods.
+ * 
+ * @author Henning Staib
+ */
+public class AbstractConnectionListener implements ConnectionListener {
+
+    public void connectionClosed() {
+        // do nothing
+    }
+
+    public void connectionClosedOnError(Exception e) {
+        // do nothing
+    }
+
+    public void reconnectingIn(int seconds) {
+        // do nothing
+    }
+
+    public void reconnectionFailed(Exception e) {
+        // do nothing
+    }
+
+    public void reconnectionSuccessful() {
+        // do nothing
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/AccountManager.java b/src/org/jivesoftware/smack/AccountManager.java
new file mode 100644
index 0000000..4d9faa5
--- /dev/null
+++ b/src/org/jivesoftware/smack/AccountManager.java
@@ -0,0 +1,337 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Registration;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Allows creation and management of accounts on an XMPP server.
+ *
+ * @see Connection#getAccountManager()
+ * @author Matt Tucker
+ */
+public class AccountManager {
+
+    private Connection connection;
+    private Registration info = null;
+
+    /**
+     * Flag that indicates whether the server supports In-Band Registration.
+     * In-Band Registration may be advertised as a stream feature. If no stream feature
+     * was advertised from the server then try sending an IQ packet to discover if In-Band
+     * Registration is available.
+     */
+    private boolean accountCreationSupported = false;
+
+    /**
+     * Creates a new AccountManager instance.
+     *
+     * @param connection a connection to a XMPP server.
+     */
+    public AccountManager(Connection connection) {
+        this.connection = connection;
+    }
+
+    /**
+     * Sets whether the server supports In-Band Registration. In-Band Registration may be
+     * advertised as a stream feature. If no stream feature was advertised from the server
+     * then try sending an IQ packet to discover if In-Band Registration is available.
+     *
+     * @param accountCreationSupported true if the server supports In-Band Registration.
+     */
+    void setSupportsAccountCreation(boolean accountCreationSupported) {
+        this.accountCreationSupported = accountCreationSupported;
+    }
+
+    /**
+     * Returns true if the server supports creating new accounts. Many servers require
+     * that you not be currently authenticated when creating new accounts, so the safest
+     * behavior is to only create new accounts before having logged in to a server.
+     *
+     * @return true if the server support creating new accounts.
+     */
+    public boolean supportsAccountCreation() {
+        // Check if we already know that the server supports creating new accounts
+        if (accountCreationSupported) {
+            return true;
+        }
+        // No information is known yet (e.g. no stream feature was received from the server
+        // indicating that it supports creating new accounts) so send an IQ packet as a way
+        // to discover if this feature is supported
+        try {
+            if (info == null) {
+                getRegistrationInfo();
+                accountCreationSupported = info.getType() != IQ.Type.ERROR;
+            }
+            return accountCreationSupported;
+        }
+        catch (XMPPException xe) {
+            return false;
+        }
+    }
+
+    /**
+     * Returns an unmodifiable collection of the names of the required account attributes.
+     * All attributes must be set when creating new accounts. The standard set of possible
+     * attributes are as follows: <ul>
+     *      <li>name -- the user's name.
+     *      <li>first -- the user's first name.
+     *      <li>last -- the user's last name.
+     *      <li>email -- the user's email address.
+     *      <li>city -- the user's city.
+     *      <li>state -- the user's state.
+     *      <li>zip -- the user's ZIP code.
+     *      <li>phone -- the user's phone number.
+     *      <li>url -- the user's website.
+     *      <li>date -- the date the registration took place.
+     *      <li>misc -- other miscellaneous information to associate with the account.
+     *      <li>text -- textual information to associate with the account.
+     *      <li>remove -- empty flag to remove account.
+     * </ul><p>
+     *
+     * Typically, servers require no attributes when creating new accounts, or just
+     * the user's email address.
+     *
+     * @return the required account attributes.
+     */
+    public Collection<String> getAccountAttributes() {
+        try {
+            if (info == null) {
+                getRegistrationInfo();
+            }
+            Map<String, String> attributes = info.getAttributes();
+            if (attributes != null) {
+                return Collections.unmodifiableSet(attributes.keySet());
+            }
+        }
+        catch (XMPPException xe) {
+            xe.printStackTrace();
+        }
+        return Collections.emptySet();
+    }
+
+    /**
+     * Returns the value of a given account attribute or <tt>null</tt> if the account
+     * attribute wasn't found.
+     *
+     * @param name the name of the account attribute to return its value.
+     * @return the value of the account attribute or <tt>null</tt> if an account
+     * attribute wasn't found for the requested name.
+     */
+    public String getAccountAttribute(String name) {
+        try {
+            if (info == null) {
+                getRegistrationInfo();
+            }
+            return info.getAttributes().get(name);
+        }
+        catch (XMPPException xe) {
+            xe.printStackTrace();
+        }
+        return null;
+    }
+
+    /**
+     * Returns the instructions for creating a new account, or <tt>null</tt> if there
+     * are no instructions. If present, instructions should be displayed to the end-user
+     * that will complete the registration process.
+     *
+     * @return the account creation instructions, or <tt>null</tt> if there are none.
+     */
+    public String getAccountInstructions() {
+        try {
+            if (info == null) {
+                getRegistrationInfo();
+            }
+            return info.getInstructions();
+        }
+        catch (XMPPException xe) {
+            return null;
+        }
+    }
+
+    /**
+     * Creates a new account using the specified username and password. The server may
+     * require a number of extra account attributes such as an email address and phone
+     * number. In that case, Smack will attempt to automatically set all required
+     * attributes with blank values, which may or may not be accepted by the server.
+     * Therefore, it's recommended to check the required account attributes and to let
+     * the end-user populate them with real values instead.
+     *
+     * @param username the username.
+     * @param password the password.
+     * @throws XMPPException if an error occurs creating the account.
+     */
+    public void createAccount(String username, String password) throws XMPPException {
+        if (!supportsAccountCreation()) {
+            throw new XMPPException("Server does not support account creation.");
+        }
+        // Create a map for all the required attributes, but give them blank values.
+        Map<String, String> attributes = new HashMap<String, String>();
+        for (String attributeName : getAccountAttributes()) {
+            attributes.put(attributeName, "");
+        }
+        createAccount(username, password, attributes);
+    }
+
+    /**
+     * Creates a new account using the specified username, password and account attributes.
+     * The attributes Map must contain only String name/value pairs and must also have values
+     * for all required attributes.
+     *
+     * @param username the username.
+     * @param password the password.
+     * @param attributes the account attributes.
+     * @throws XMPPException if an error occurs creating the account.
+     * @see #getAccountAttributes()
+     */
+    public void createAccount(String username, String password, Map<String, String> attributes)
+            throws XMPPException
+    {
+        if (!supportsAccountCreation()) {
+            throw new XMPPException("Server does not support account creation.");
+        }
+        Registration reg = new Registration();
+        reg.setType(IQ.Type.SET);
+        reg.setTo(connection.getServiceName());
+        attributes.put("username",username);
+        attributes.put("password",password);
+        reg.setAttributes(attributes);
+        PacketFilter filter = new AndFilter(new PacketIDFilter(reg.getPacketID()),
+                new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+    }
+
+    /**
+     * Changes the password of the currently logged-in account. This operation can only
+     * be performed after a successful login operation has been completed. Not all servers
+     * support changing passwords; an XMPPException will be thrown when that is the case.
+     *
+     * @throws IllegalStateException if not currently logged-in to the server.
+     * @throws XMPPException if an error occurs when changing the password.
+     */
+    public void changePassword(String newPassword) throws XMPPException {
+        Registration reg = new Registration();
+        reg.setType(IQ.Type.SET);
+        reg.setTo(connection.getServiceName());
+        Map<String, String> map = new HashMap<String, String>();
+        map.put("username",StringUtils.parseName(connection.getUser()));
+        map.put("password",newPassword);
+        reg.setAttributes(map);
+        PacketFilter filter = new AndFilter(new PacketIDFilter(reg.getPacketID()),
+                new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+    }
+
+    /**
+     * Deletes the currently logged-in account from the server. This operation can only
+     * be performed after a successful login operation has been completed. Not all servers
+     * support deleting accounts; an XMPPException will be thrown when that is the case.
+     *
+     * @throws IllegalStateException if not currently logged-in to the server.
+     * @throws XMPPException if an error occurs when deleting the account.
+     */
+    public void deleteAccount() throws XMPPException {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Must be logged in to delete a account.");
+        }
+        Registration reg = new Registration();
+        reg.setType(IQ.Type.SET);
+        reg.setTo(connection.getServiceName());
+        Map<String, String> attributes = new HashMap<String, String>();
+        // To delete an account, we add a single attribute, "remove", that is blank.
+        attributes.put("remove", "");
+        reg.setAttributes(attributes);
+        PacketFilter filter = new AndFilter(new PacketIDFilter(reg.getPacketID()),
+                new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+    }
+
+    /**
+     * Gets the account registration info from the server.
+     *
+     * @throws XMPPException if an error occurs.
+     */
+    private synchronized void getRegistrationInfo() throws XMPPException {
+        Registration reg = new Registration();
+        reg.setTo(connection.getServiceName());
+        PacketFilter filter = new AndFilter(new PacketIDFilter(reg.getPacketID()),
+                new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+        else {
+            info = (Registration)result;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/AndroidConnectionConfiguration.java b/src/org/jivesoftware/smack/AndroidConnectionConfiguration.java
new file mode 100644
index 0000000..6ec05e0
--- /dev/null
+++ b/src/org/jivesoftware/smack/AndroidConnectionConfiguration.java
@@ -0,0 +1,113 @@
+package org.jivesoftware.smack;
+
+import java.io.File;
+
+import android.os.Build;
+
+import org.jivesoftware.smack.proxy.ProxyInfo;
+import org.jivesoftware.smack.util.DNSUtil;
+import org.jivesoftware.smack.util.dns.HostAddress;
+
+import java.util.List;
+
+/**
+ * This class wraps DNS SRV lookups for a new ConnectionConfiguration in a 
+ * new thread, since Android API >= 11 (Honeycomb) does not allow network 
+ * activity in the main thread. 
+ * 
+ * @author Florian Schmaus fschmaus@gmail.com
+ *
+ */
+public class AndroidConnectionConfiguration extends ConnectionConfiguration {
+    private static final int DEFAULT_TIMEOUT = 10000;
+    
+    /**
+     * Creates a new ConnectionConfiguration for the specified service name.
+     * A DNS SRV lookup will be performed to find out the actual host address
+     * and port to use for the connection.
+     *
+     * @param serviceName the name of the service provided by an XMPP server.
+     */
+    public AndroidConnectionConfiguration(String serviceName) throws XMPPException {
+        super();
+        AndroidInit(serviceName, DEFAULT_TIMEOUT);
+    }
+    
+    /**
+     * 
+     * @param serviceName
+     * @param timeout
+     * @throws XMPPException
+     */
+    public AndroidConnectionConfiguration(String serviceName, int timeout) throws XMPPException {
+        super();
+        AndroidInit(serviceName, timeout);
+    }
+
+    public AndroidConnectionConfiguration(String host, int port, String name) {
+	super(host, port, name);
+	AndroidInit();
+    }
+
+    private void AndroidInit() {
+    	// API 14 is Ice Cream Sandwich
+	if (Build.VERSION.SDK_INT >= 14) {
+	    setTruststoreType("AndroidCAStore");
+	    setTruststorePassword(null);
+	    setTruststorePath(null);
+	} else {
+	    setTruststoreType("BKS");
+	    String path = System.getProperty("javax.net.ssl.trustStore");
+	    if (path == null)
+		path = System.getProperty("java.home") + File.separator + "etc"
+		    + File.separator + "security" + File.separator
+		    + "cacerts.bks";
+	    setTruststorePath(path);
+	}
+    }
+
+    /**
+     * 
+     * @param serviceName
+     * @param timeout
+     * @throws XMPPException
+     */
+    private void AndroidInit(String serviceName, int timeout) throws XMPPException {
+	AndroidInit();
+        class DnsSrvLookupRunnable implements Runnable {
+            String serviceName;
+            List<HostAddress> addresses;
+
+            public DnsSrvLookupRunnable(String serviceName) {
+                this.serviceName = serviceName;
+            }
+
+            @Override
+            public void run() {
+                addresses = DNSUtil.resolveXMPPDomain(serviceName);
+            }
+
+            public List<HostAddress> getHostAddresses() {
+                return addresses;
+            }
+        }
+
+        DnsSrvLookupRunnable dnsSrv = new DnsSrvLookupRunnable(serviceName);
+        Thread t = new Thread(dnsSrv, "dns-srv-lookup");
+        t.start();
+        try {
+            t.join(timeout);
+        } catch (InterruptedException e) {
+            throw new XMPPException("DNS lookup timeout after " + timeout + "ms", e);
+        }
+
+        hostAddresses = dnsSrv.getHostAddresses();
+        if (hostAddresses == null) {
+        	throw new XMPPException("DNS lookup failure");
+        }
+
+        ProxyInfo proxy = ProxyInfo.forDefaultProxy();
+
+        init(serviceName, proxy);
+    }
+}
diff --git a/src/org/jivesoftware/smack/BOSHConfiguration.java b/src/org/jivesoftware/smack/BOSHConfiguration.java
new file mode 100644
index 0000000..0b033b4
--- /dev/null
+++ b/src/org/jivesoftware/smack/BOSHConfiguration.java
@@ -0,0 +1,124 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.net.URI;
+import java.net.URISyntaxException;
+
+import org.jivesoftware.smack.ConnectionConfiguration;
+import org.jivesoftware.smack.proxy.ProxyInfo;
+
+/**
+ * Configuration to use while establishing the connection to the XMPP server via
+ * HTTP binding.
+ * 
+ * @see BOSHConnection
+ * @author Guenther Niess
+ */
+public class BOSHConfiguration extends ConnectionConfiguration {
+
+    private boolean ssl;
+    private String file;
+
+    public BOSHConfiguration(String xmppDomain) {
+        super(xmppDomain, 7070);
+        setSASLAuthenticationEnabled(true);
+        ssl = false;
+        file = "/http-bind/";
+    }
+
+    public BOSHConfiguration(String xmppDomain, int port) {
+        super(xmppDomain, port);
+        setSASLAuthenticationEnabled(true);
+        ssl = false;
+        file = "/http-bind/";
+    }
+
+    /**
+     * Create a HTTP Binding configuration.
+     * 
+     * @param https true if you want to use SSL
+     *             (e.g. false for http://domain.lt:7070/http-bind).
+     * @param host the hostname or IP address of the connection manager
+     *             (e.g. domain.lt for http://domain.lt:7070/http-bind).
+     * @param port the port of the connection manager
+     *             (e.g. 7070 for http://domain.lt:7070/http-bind).
+     * @param filePath the file which is described by the URL
+     *             (e.g. /http-bind for http://domain.lt:7070/http-bind).
+     * @param xmppDomain the XMPP service name
+     *             (e.g. domain.lt for the user alice@domain.lt)
+     */
+    public BOSHConfiguration(boolean https, String host, int port, String filePath, String xmppDomain) {
+        super(host, port, xmppDomain);
+        setSASLAuthenticationEnabled(true);
+        ssl = https;
+        file = (filePath != null ? filePath : "/");
+    }
+
+    /**
+     * Create a HTTP Binding configuration.
+     * 
+     * @param https true if you want to use SSL
+     *             (e.g. false for http://domain.lt:7070/http-bind).
+     * @param host the hostname or IP address of the connection manager
+     *             (e.g. domain.lt for http://domain.lt:7070/http-bind).
+     * @param port the port of the connection manager
+     *             (e.g. 7070 for http://domain.lt:7070/http-bind).
+     * @param filePath the file which is described by the URL
+     *             (e.g. /http-bind for http://domain.lt:7070/http-bind).
+     * @param proxy the configuration of a proxy server.
+     * @param xmppDomain the XMPP service name
+     *             (e.g. domain.lt for the user alice@domain.lt)
+     */
+    public BOSHConfiguration(boolean https, String host, int port, String filePath, ProxyInfo proxy, String xmppDomain) {
+        super(host, port, xmppDomain, proxy);
+        setSASLAuthenticationEnabled(true);
+        ssl = https;
+        file = (filePath != null ? filePath : "/");
+    }
+
+    public boolean isProxyEnabled() {
+        return (proxy != null && proxy.getProxyType() != ProxyInfo.ProxyType.NONE);
+    }
+
+    public ProxyInfo getProxyInfo() {
+        return proxy;
+    }
+
+    public String getProxyAddress() {
+        return (proxy != null ? proxy.getProxyAddress() : null);
+    }
+
+    public int getProxyPort() {
+        return (proxy != null ? proxy.getProxyPort() : 8080);
+    }
+
+    public boolean isUsingSSL() {
+        return ssl;
+    }
+
+    public URI getURI() throws URISyntaxException {
+        if (file.charAt(0) != '/') {
+            file = '/' + file;
+        }
+        return new URI((ssl ? "https://" : "http://") + getHost() + ":" + getPort() + file);
+    }
+}
diff --git a/src/org/jivesoftware/smack/BOSHConnection.java b/src/org/jivesoftware/smack/BOSHConnection.java
new file mode 100644
index 0000000..594cf9d
--- /dev/null
+++ b/src/org/jivesoftware/smack/BOSHConnection.java
@@ -0,0 +1,779 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.io.IOException;
+import java.io.PipedReader;
+import java.io.PipedWriter;
+import java.io.Writer;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.ThreadFactory;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.Roster;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+
+import com.kenai.jbosh.BOSHClient;
+import com.kenai.jbosh.BOSHClientConfig;
+import com.kenai.jbosh.BOSHClientConnEvent;
+import com.kenai.jbosh.BOSHClientConnListener;
+import com.kenai.jbosh.BOSHClientRequestListener;
+import com.kenai.jbosh.BOSHClientResponseListener;
+import com.kenai.jbosh.BOSHException;
+import com.kenai.jbosh.BOSHMessageEvent;
+import com.kenai.jbosh.BodyQName;
+import com.kenai.jbosh.ComposableBody;
+
+/**
+ * Creates a connection to a XMPP server via HTTP binding.
+ * This is specified in the XEP-0206: XMPP Over BOSH.
+ * 
+ * @see Connection
+ * @author Guenther Niess
+ */
+public class BOSHConnection extends Connection {
+
+    /**
+     * The XMPP Over Bosh namespace.
+     */
+    public static final String XMPP_BOSH_NS = "urn:xmpp:xbosh";
+
+    /**
+     * The BOSH namespace from XEP-0124.
+     */
+    public static final String BOSH_URI = "http://jabber.org/protocol/httpbind";
+
+    /**
+     * The used BOSH client from the jbosh library.
+     */
+    private BOSHClient client;
+
+    /**
+     * Holds the initial configuration used while creating the connection.
+     */
+    private final BOSHConfiguration config;
+
+    // Some flags which provides some info about the current state.
+    private boolean connected = false;
+    private boolean authenticated = false;
+    private boolean anonymous = false;
+    private boolean isFirstInitialization = true;
+    private boolean wasAuthenticated = false;
+    private boolean done = false;
+
+    /**
+     * The Thread environment for sending packet listeners.
+     */
+    private ExecutorService listenerExecutor;
+
+    // The readerPipe and consumer thread are used for the debugger.
+    private PipedWriter readerPipe;
+    private Thread readerConsumer;
+
+    /**
+     * The BOSH equivalent of the stream ID which is used for DIGEST authentication.
+     */
+    protected String authID = null;
+
+    /**
+     * The session ID for the BOSH session with the connection manager.
+     */
+    protected String sessionID = null;
+
+    /**
+     * The full JID of the authenticated user.
+     */
+    private String user = null;
+
+    /**
+     * The roster maybe also called buddy list holds the list of the users contacts.
+     */
+    private Roster roster = null;
+
+
+    /**
+     * Create a HTTP Binding connection to a XMPP server.
+     * 
+     * @param https true if you want to use SSL
+     *             (e.g. false for http://domain.lt:7070/http-bind).
+     * @param host the hostname or IP address of the connection manager
+     *             (e.g. domain.lt for http://domain.lt:7070/http-bind).
+     * @param port the port of the connection manager
+     *             (e.g. 7070 for http://domain.lt:7070/http-bind).
+     * @param filePath the file which is described by the URL
+     *             (e.g. /http-bind for http://domain.lt:7070/http-bind).
+     * @param xmppDomain the XMPP service name
+     *             (e.g. domain.lt for the user alice@domain.lt)
+     */
+    public BOSHConnection(boolean https, String host, int port, String filePath, String xmppDomain) {
+        super(new BOSHConfiguration(https, host, port, filePath, xmppDomain));
+        this.config = (BOSHConfiguration) getConfiguration();
+    }
+
+    /**
+     * Create a HTTP Binding connection to a XMPP server.
+     * 
+     * @param config The configuration which is used for this connection.
+     */
+    public BOSHConnection(BOSHConfiguration config) {
+        super(config);
+        this.config = config;
+    }
+
+    public void connect() throws XMPPException {
+        if (connected) {
+            throw new IllegalStateException("Already connected to a server.");
+        }
+        done = false;
+        try {
+            // Ensure a clean starting state
+            if (client != null) {
+                client.close();
+                client = null;
+            }
+            saslAuthentication.init();
+            sessionID = null;
+            authID = null;
+
+            // Initialize BOSH client
+            BOSHClientConfig.Builder cfgBuilder = BOSHClientConfig.Builder
+                    .create(config.getURI(), config.getServiceName());
+            if (config.isProxyEnabled()) {
+                cfgBuilder.setProxy(config.getProxyAddress(), config.getProxyPort());
+            }
+            client = BOSHClient.create(cfgBuilder.build());
+
+            // Create an executor to deliver incoming packets to listeners.
+            // We'll use a single thread with an unbounded queue.
+            listenerExecutor = Executors
+                    .newSingleThreadExecutor(new ThreadFactory() {
+                        public Thread newThread(Runnable runnable) {
+                            Thread thread = new Thread(runnable,
+                                    "Smack Listener Processor ("
+                                            + connectionCounterValue + ")");
+                            thread.setDaemon(true);
+                            return thread;
+                        }
+                    });
+            client.addBOSHClientConnListener(new BOSHConnectionListener(this));
+            client.addBOSHClientResponseListener(new BOSHPacketReader(this));
+
+            // Initialize the debugger
+            if (config.isDebuggerEnabled()) {
+                initDebugger();
+                if (isFirstInitialization) {
+                    if (debugger.getReaderListener() != null) {
+                        addPacketListener(debugger.getReaderListener(), null);
+                    }
+                    if (debugger.getWriterListener() != null) {
+                        addPacketSendingListener(debugger.getWriterListener(), null);
+                    }
+                }
+            }
+
+            // Send the session creation request
+            client.send(ComposableBody.builder()
+                    .setNamespaceDefinition("xmpp", XMPP_BOSH_NS)
+                    .setAttribute(BodyQName.createWithPrefix(XMPP_BOSH_NS, "version", "xmpp"), "1.0")
+                    .build());
+        } catch (Exception e) {
+            throw new XMPPException("Can't connect to " + getServiceName(), e);
+        }
+
+        // Wait for the response from the server
+        synchronized (this) {
+            long endTime = System.currentTimeMillis() +
+                           SmackConfiguration.getPacketReplyTimeout() * 6;
+            while ((!connected) && (System.currentTimeMillis() < endTime)) {
+                try {
+                    wait(Math.abs(endTime - System.currentTimeMillis()));
+                }
+                catch (InterruptedException e) {}
+            }
+        }
+
+        // If there is no feedback, throw an remote server timeout error
+        if (!connected && !done) {
+            done = true;
+            String errorMessage = "Timeout reached for the connection to " 
+                    + getHost() + ":" + getPort() + ".";
+            throw new XMPPException(
+                    errorMessage,
+                    new XMPPError(XMPPError.Condition.remote_server_timeout, errorMessage));
+        }
+    }
+
+    public String getConnectionID() {
+        if (!connected) {
+            return null;
+        } else if (authID != null) {
+            return authID;
+        } else {
+            return sessionID;
+        }
+    }
+
+    public Roster getRoster() {
+        if (roster == null) {
+            return null;
+        }
+        if (!config.isRosterLoadedAtLogin()) {
+            roster.reload();
+        }
+        // If this is the first time the user has asked for the roster after calling
+        // login, we want to wait for the server to send back the user's roster.
+        // This behavior shields API users from having to worry about the fact that
+        // roster operations are asynchronous, although they'll still have to listen
+        // for changes to the roster. Note: because of this waiting logic, internal
+        // Smack code should be wary about calling the getRoster method, and may
+        // need to access the roster object directly.
+        if (!roster.rosterInitialized) {
+            try {
+                synchronized (roster) {
+                    long waitTime = SmackConfiguration.getPacketReplyTimeout();
+                    long start = System.currentTimeMillis();
+                    while (!roster.rosterInitialized) {
+                        if (waitTime <= 0) {
+                            break;
+                        }
+                        roster.wait(waitTime);
+                        long now = System.currentTimeMillis();
+                        waitTime -= now - start;
+                        start = now;
+                    }
+                }
+            } catch (InterruptedException ie) {
+                // Ignore.
+            }
+        }
+        return roster;
+    }
+
+    public String getUser() {
+        return user;
+    }
+
+    public boolean isAnonymous() {
+        return anonymous;
+    }
+
+    public boolean isAuthenticated() {
+        return authenticated;
+    }
+
+    public boolean isConnected() {
+        return connected;
+    }
+
+    public boolean isSecureConnection() {
+        // TODO: Implement SSL usage
+        return false;
+    }
+
+    public boolean isUsingCompression() {
+        // TODO: Implement compression
+        return false;
+    }
+
+    public void login(String username, String password, String resource)
+            throws XMPPException {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (authenticated) {
+            throw new IllegalStateException("Already logged in to server.");
+        }
+        // Do partial version of nameprep on the username.
+        username = username.toLowerCase().trim();
+
+        String response;
+        if (config.isSASLAuthenticationEnabled()
+                && saslAuthentication.hasNonAnonymousAuthentication()) {
+            // Authenticate using SASL
+            if (password != null) {
+                response = saslAuthentication.authenticate(username, password, resource);
+            } else {
+                response = saslAuthentication.authenticate(username, resource, config.getCallbackHandler());
+            }
+        } else {
+            // Authenticate using Non-SASL
+            response = new NonSASLAuthentication(this).authenticate(username, password, resource);
+        }
+
+        // Set the user.
+        if (response != null) {
+            this.user = response;
+            // Update the serviceName with the one returned by the server
+            config.setServiceName(StringUtils.parseServer(response));
+        } else {
+            this.user = username + "@" + getServiceName();
+            if (resource != null) {
+                this.user += "/" + resource;
+            }
+        }
+
+        // Create the roster if it is not a reconnection.
+        if (this.roster == null) {
+            if (this.rosterStorage == null) {
+                this.roster = new Roster(this);
+            } else {
+                this.roster = new Roster(this, rosterStorage);
+            }
+        }
+
+        // Set presence to online.
+        if (config.isSendPresence()) {
+            sendPacket(new Presence(Presence.Type.available));
+        }
+
+        // Indicate that we're now authenticated.
+        authenticated = true;
+        anonymous = false;
+
+        if (config.isRosterLoadedAtLogin()) {
+            this.roster.reload();
+        }
+        // Stores the autentication for future reconnection
+        config.setLoginInfo(username, password, resource);
+
+        // If debugging is enabled, change the the debug window title to include
+        // the
+        // name we are now logged-in as.l
+        if (config.isDebuggerEnabled() && debugger != null) {
+            debugger.userHasLogged(user);
+        }
+    }
+
+    public void loginAnonymously() throws XMPPException {
+    	if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (authenticated) {
+            throw new IllegalStateException("Already logged in to server.");
+        }
+
+        String response;
+        if (config.isSASLAuthenticationEnabled() &&
+                saslAuthentication.hasAnonymousAuthentication()) {
+            response = saslAuthentication.authenticateAnonymously();
+        }
+        else {
+            // Authenticate using Non-SASL
+            response = new NonSASLAuthentication(this).authenticateAnonymously();
+        }
+
+        // Set the user value.
+        this.user = response;
+        // Update the serviceName with the one returned by the server
+        config.setServiceName(StringUtils.parseServer(response));
+
+        // Anonymous users can't have a roster.
+        roster = null;
+
+        // Set presence to online.
+        if (config.isSendPresence()) {
+            sendPacket(new Presence(Presence.Type.available));
+        }
+
+        // Indicate that we're now authenticated.
+        authenticated = true;
+        anonymous = true;
+
+        // If debugging is enabled, change the the debug window title to include the
+        // name we are now logged-in as.
+        // If DEBUG_ENABLED was set to true AFTER the connection was created the debugger
+        // will be null
+        if (config.isDebuggerEnabled() && debugger != null) {
+            debugger.userHasLogged(user);
+        }
+    }
+
+    public void sendPacket(Packet packet) {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (packet == null) {
+            throw new NullPointerException("Packet is null.");
+        }
+        if (!done) {
+            // Invoke interceptors for the new packet that is about to be sent.
+            // Interceptors
+            // may modify the content of the packet.
+            firePacketInterceptors(packet);
+
+            try {
+                send(ComposableBody.builder().setPayloadXML(packet.toXML())
+                        .build());
+            } catch (BOSHException e) {
+                e.printStackTrace();
+                return;
+            }
+
+            // Process packet writer listeners. Note that we're using the
+            // sending
+            // thread so it's expected that listeners are fast.
+            firePacketSendingListeners(packet);
+        }
+    }
+
+    public void disconnect(Presence unavailablePresence) {
+        if (!connected) {
+            return;
+        }
+        shutdown(unavailablePresence);
+
+        // Cleanup
+        if (roster != null) {
+            roster.cleanup();
+            roster = null;
+        }
+        sendListeners.clear();
+        recvListeners.clear();
+        collectors.clear();
+        interceptors.clear();
+
+        // Reset the connection flags
+        wasAuthenticated = false;
+        isFirstInitialization = true;
+
+        // Notify connection listeners of the connection closing if done hasn't already been set.
+        for (ConnectionListener listener : getConnectionListeners()) {
+            try {
+                listener.connectionClosed();
+            }
+            catch (Exception e) {
+                // Catch and print any exception so we can recover
+                // from a faulty listener and finish the shutdown process
+                e.printStackTrace();
+            }
+        }
+    }
+
+    /**
+     * Closes the connection by setting presence to unavailable and closing the 
+     * HTTP client. The shutdown logic will be used during a planned disconnection or when
+     * dealing with an unexpected disconnection. Unlike {@link #disconnect()} the connection's
+     * BOSH packet reader and {@link Roster} will not be removed; thus
+     * connection's state is kept.
+     *
+     * @param unavailablePresence the presence packet to send during shutdown.
+     */
+    protected void shutdown(Presence unavailablePresence) {
+        setWasAuthenticated(authenticated);
+        authID = null;
+        sessionID = null;
+        done = true;
+        authenticated = false;
+        connected = false;
+        isFirstInitialization = false;
+
+        try {
+            client.disconnect(ComposableBody.builder()
+                    .setNamespaceDefinition("xmpp", XMPP_BOSH_NS)
+                    .setPayloadXML(unavailablePresence.toXML())
+                    .build());
+            // Wait 150 ms for processes to clean-up, then shutdown.
+            Thread.sleep(150);
+        }
+        catch (Exception e) {
+            // Ignore.
+        }
+
+        // Close down the readers and writers.
+        if (readerPipe != null) {
+            try {
+                readerPipe.close();
+            }
+            catch (Throwable ignore) { /* ignore */ }
+            reader = null;
+        }
+        if (reader != null) {
+            try {
+                reader.close();
+            }
+            catch (Throwable ignore) { /* ignore */ }
+            reader = null;
+        }
+        if (writer != null) {
+            try {
+                writer.close();
+            }
+            catch (Throwable ignore) { /* ignore */ }
+            writer = null;
+        }
+
+        // Shut down the listener executor.
+        if (listenerExecutor != null) {
+            listenerExecutor.shutdown();
+        }
+        readerConsumer = null;
+    }
+
+    /**
+     * Sets whether the connection has already logged in the server.
+     *
+     * @param wasAuthenticated true if the connection has already been authenticated.
+     */
+    private void setWasAuthenticated(boolean wasAuthenticated) {
+        if (!this.wasAuthenticated) {
+            this.wasAuthenticated = wasAuthenticated;
+        }
+    }
+
+    /**
+     * Send a HTTP request to the connection manager with the provided body element.
+     * 
+     * @param body the body which will be sent.
+     */
+    protected void send(ComposableBody body) throws BOSHException {
+        if (!connected) {
+            throw new IllegalStateException("Not connected to a server!");
+        }
+        if (body == null) {
+            throw new NullPointerException("Body mustn't be null!");
+        }
+        if (sessionID != null) {
+            body = body.rebuild().setAttribute(
+                    BodyQName.create(BOSH_URI, "sid"), sessionID).build();
+        }
+        client.send(body);
+    }
+
+    /**
+     * Processes a packet after it's been fully parsed by looping through the
+     * installed packet collectors and listeners and letting them examine the
+     * packet to see if they are a match with the filter.
+     * 
+     * @param packet the packet to process.
+     */
+    protected void processPacket(Packet packet) {
+        if (packet == null) {
+            return;
+        }
+
+        // Loop through all collectors and notify the appropriate ones.
+        for (PacketCollector collector : getPacketCollectors()) {
+            collector.processPacket(packet);
+        }
+
+        // Deliver the incoming packet to listeners.
+        listenerExecutor.submit(new ListenerNotification(packet));
+    }
+
+    /**
+     * Initialize the SmackDebugger which allows to log and debug XML traffic.
+     */
+    protected void initDebugger() {
+        // TODO: Maybe we want to extend the SmackDebugger for simplification
+        //       and a performance boost.
+
+        // Initialize a empty writer which discards all data.
+        writer = new Writer() {
+                public void write(char[] cbuf, int off, int len) { /* ignore */}
+                public void close() { /* ignore */ }
+                public void flush() { /* ignore */ }
+            };
+
+        // Initialize a pipe for received raw data.
+        try {
+            readerPipe = new PipedWriter();
+            reader = new PipedReader(readerPipe);
+        }
+        catch (IOException e) {
+            // Ignore
+        }
+
+        // Call the method from the parent class which initializes the debugger.
+        super.initDebugger();
+
+        // Add listeners for the received and sent raw data.
+        client.addBOSHClientResponseListener(new BOSHClientResponseListener() {
+            public void responseReceived(BOSHMessageEvent event) {
+                if (event.getBody() != null) {
+                    try {
+                        readerPipe.write(event.getBody().toXML());
+                        readerPipe.flush();
+                    } catch (Exception e) {
+                        // Ignore
+                    }
+                }
+            }
+        });
+        client.addBOSHClientRequestListener(new BOSHClientRequestListener() {
+            public void requestSent(BOSHMessageEvent event) {
+                if (event.getBody() != null) {
+                    try {
+                        writer.write(event.getBody().toXML());
+                    } catch (Exception e) {
+                        // Ignore
+                    }
+                }
+            }
+        });
+
+        // Create and start a thread which discards all read data.
+        readerConsumer = new Thread() {
+            private Thread thread = this;
+            private int bufferLength = 1024;
+
+            public void run() {
+                try {
+                    char[] cbuf = new char[bufferLength];
+                    while (readerConsumer == thread && !done) {
+                        reader.read(cbuf, 0, bufferLength);
+                    }
+                } catch (IOException e) {
+                    // Ignore
+                }
+            }
+        };
+        readerConsumer.setDaemon(true);
+        readerConsumer.start();
+    }
+
+    /**
+     * Sends out a notification that there was an error with the connection
+     * and closes the connection.
+     *
+     * @param e the exception that causes the connection close event.
+     */
+    protected void notifyConnectionError(Exception e) {
+        // Closes the connection temporary. A reconnection is possible
+        shutdown(new Presence(Presence.Type.unavailable));
+        // Print the stack trace to help catch the problem
+        e.printStackTrace();
+        // Notify connection listeners of the error.
+        for (ConnectionListener listener : getConnectionListeners()) {
+            try {
+                listener.connectionClosedOnError(e);
+            }
+            catch (Exception e2) {
+                // Catch and print any exception so we can recover
+                // from a faulty listener
+                e2.printStackTrace();
+            }
+        }
+    }
+
+
+    /**
+     * A listener class which listen for a successfully established connection
+     * and connection errors and notifies the BOSHConnection.
+     * 
+     * @author Guenther Niess
+     */
+    private class BOSHConnectionListener implements BOSHClientConnListener {
+
+        private final BOSHConnection connection;
+
+        public BOSHConnectionListener(BOSHConnection connection) {
+            this.connection = connection;
+        }
+
+        /**
+         * Notify the BOSHConnection about connection state changes.
+         * Process the connection listeners and try to login if the
+         * connection was formerly authenticated and is now reconnected.
+         */
+        public void connectionEvent(BOSHClientConnEvent connEvent) {
+            try {
+                if (connEvent.isConnected()) {
+                    connected = true;
+                    if (isFirstInitialization) {
+                        isFirstInitialization = false;
+                        for (ConnectionCreationListener listener : getConnectionCreationListeners()) {
+                            listener.connectionCreated(connection);
+                        }
+                    }
+                    else {
+                        try {
+                            if (wasAuthenticated) {
+                                connection.login(
+                                        config.getUsername(),
+                                        config.getPassword(),
+                                        config.getResource());
+                            }
+                            for (ConnectionListener listener : getConnectionListeners()) {
+                                 listener.reconnectionSuccessful();
+                            }
+                        }
+                        catch (XMPPException e) {
+                            for (ConnectionListener listener : getConnectionListeners()) {
+                                listener.reconnectionFailed(e);
+                           }
+                        }
+                    }
+                }
+                else {
+                    if (connEvent.isError()) {
+                        try {
+                            connEvent.getCause();
+                        }
+                        catch (Exception e) {
+                            notifyConnectionError(e);
+                        }
+                    }
+                    connected = false;
+                }
+            }
+            finally {
+                synchronized (connection) {
+                    connection.notifyAll();
+                }
+            }
+        }
+    }
+
+    /**
+     * This class notifies all listeners that a packet was received.
+     */
+    private class ListenerNotification implements Runnable {
+
+        private Packet packet;
+
+        public ListenerNotification(Packet packet) {
+            this.packet = packet;
+        }
+
+        public void run() {
+            for (ListenerWrapper listenerWrapper : recvListeners.values()) {
+                listenerWrapper.notifyListener(packet);
+            }
+        }
+    }
+
+	@Override
+	public void setRosterStorage(RosterStorage storage)
+			throws IllegalStateException {
+		if(this.roster!=null){
+			throw new IllegalStateException("Roster is already initialized");
+		}
+		this.rosterStorage = storage;
+	}
+}
diff --git a/src/org/jivesoftware/smack/BOSHPacketReader.java b/src/org/jivesoftware/smack/BOSHPacketReader.java
new file mode 100644
index 0000000..c86d756
--- /dev/null
+++ b/src/org/jivesoftware/smack/BOSHPacketReader.java
@@ -0,0 +1,169 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.io.StringReader;
+
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smack.sasl.SASLMechanism.Challenge;
+import org.jivesoftware.smack.sasl.SASLMechanism.Failure;
+import org.jivesoftware.smack.sasl.SASLMechanism.Success;
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+
+import com.kenai.jbosh.AbstractBody;
+import com.kenai.jbosh.BOSHClientResponseListener;
+import com.kenai.jbosh.BOSHMessageEvent;
+import com.kenai.jbosh.BodyQName;
+import com.kenai.jbosh.ComposableBody;
+
+/**
+ * Listens for XML traffic from the BOSH connection manager and parses it into
+ * packet objects.
+ * 
+ * @author Guenther Niess
+ */
+public class BOSHPacketReader implements BOSHClientResponseListener {
+
+    private BOSHConnection connection;
+
+    /**
+     * Create a packet reader which listen on a BOSHConnection for received
+     * HTTP responses, parse the packets and notifies the connection.
+     * 
+     * @param connection the corresponding connection for the received packets.
+     */
+    public BOSHPacketReader(BOSHConnection connection) {
+        this.connection = connection;
+    }
+
+    /**
+     * Parse the received packets and notify the corresponding connection.
+     * 
+     * @param event the BOSH client response which includes the received packet.
+     */
+    public void responseReceived(BOSHMessageEvent event) {
+        AbstractBody body = event.getBody();
+        if (body != null) {
+            try {
+                if (connection.sessionID == null) {
+                    connection.sessionID = body.getAttribute(BodyQName.create(BOSHConnection.BOSH_URI, "sid"));
+                }
+                if (connection.authID == null) {
+                    connection.authID = body.getAttribute(BodyQName.create(BOSHConnection.BOSH_URI, "authid"));
+                }
+                final XmlPullParser parser = XmlPullParserFactory.newInstance().newPullParser();
+                parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES,
+                        true);
+                parser.setInput(new StringReader(body.toXML()));
+                int eventType = parser.getEventType();
+                do {
+                    eventType = parser.next();
+                    if (eventType == XmlPullParser.START_TAG) {
+                        if (parser.getName().equals("body")) {
+                            // ignore the container root element
+                        } else if (parser.getName().equals("message")) {
+                            connection.processPacket(PacketParserUtils.parseMessage(parser));
+                        } else if (parser.getName().equals("iq")) {
+                            connection.processPacket(PacketParserUtils.parseIQ(parser, connection));
+                        } else if (parser.getName().equals("presence")) {
+                            connection.processPacket(PacketParserUtils.parsePresence(parser));
+                        } else if (parser.getName().equals("challenge")) {
+                            // The server is challenging the SASL authentication
+                            // made by the client
+                            final String challengeData = parser.nextText();
+                            connection.getSASLAuthentication()
+                                    .challengeReceived(challengeData);
+                            connection.processPacket(new Challenge(
+                                    challengeData));
+                        } else if (parser.getName().equals("success")) {
+                            connection.send(ComposableBody.builder()
+                                    .setNamespaceDefinition("xmpp", BOSHConnection.XMPP_BOSH_NS)
+                                    .setAttribute(
+                                            BodyQName.createWithPrefix(BOSHConnection.XMPP_BOSH_NS, "restart", "xmpp"),
+                                            "true")
+                                    .setAttribute(
+                                            BodyQName.create(BOSHConnection.BOSH_URI, "to"),
+                                            connection.getServiceName())
+                                    .build());
+                            connection.getSASLAuthentication().authenticated();
+                            connection.processPacket(new Success(parser.nextText()));
+                        } else if (parser.getName().equals("features")) {
+                            parseFeatures(parser);
+                        } else if (parser.getName().equals("failure")) {
+                            if ("urn:ietf:params:xml:ns:xmpp-sasl".equals(parser.getNamespace(null))) {
+                                final Failure failure = PacketParserUtils.parseSASLFailure(parser);
+                                connection.getSASLAuthentication().authenticationFailed();
+                                connection.processPacket(failure);
+                            }
+                        } else if (parser.getName().equals("error")) {
+                            throw new XMPPException(PacketParserUtils.parseStreamError(parser));
+                        }
+                    }
+                } while (eventType != XmlPullParser.END_DOCUMENT);
+            }
+            catch (Exception e) {
+                if (connection.isConnected()) {
+                    connection.notifyConnectionError(e);
+                }
+            }
+        }
+    }
+
+    /**
+     * Parse and setup the XML stream features.
+     * 
+     * @param parser the XML parser, positioned at the start of a message packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    private void parseFeatures(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("mechanisms")) {
+                    // The server is reporting available SASL mechanisms. Store
+                    // this information
+                    // which will be used later while logging (i.e.
+                    // authenticating) into
+                    // the server
+                    connection.getSASLAuthentication().setAvailableSASLMethods(
+                            PacketParserUtils.parseMechanisms(parser));
+                } else if (parser.getName().equals("bind")) {
+                    // The server requires the client to bind a resource to the
+                    // stream
+                    connection.getSASLAuthentication().bindingRequired();
+                } else if (parser.getName().equals("session")) {
+                    // The server supports sessions
+                    connection.getSASLAuthentication().sessionsSupported();
+                } else if (parser.getName().equals("register")) {
+                    connection.getAccountManager().setSupportsAccountCreation(
+                            true);
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("features")) {
+                    done = true;
+                }
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/Chat.java b/src/org/jivesoftware/smack/Chat.java
new file mode 100644
index 0000000..66f5a54
--- /dev/null
+++ b/src/org/jivesoftware/smack/Chat.java
@@ -0,0 +1,180 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Message;
+
+import java.util.Set;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+/**
+ * A chat is a series of messages sent between two users. Each chat has a unique
+ * thread ID, which is used to track which messages are part of a particular
+ * conversation. Some messages are sent without a thread ID, and some clients
+ * don't send thread IDs at all. Therefore, if a message without a thread ID
+ * arrives it is routed to the most recently created Chat with the message
+ * sender.
+ * 
+ * @author Matt Tucker
+ */
+public class Chat {
+
+    private ChatManager chatManager;
+    private String threadID;
+    private String participant;
+    private final Set<MessageListener> listeners = new CopyOnWriteArraySet<MessageListener>();
+
+    /**
+     * Creates a new chat with the specified user and thread ID.
+     *
+     * @param chatManager the chatManager the chat will use.
+     * @param participant the user to chat with.
+     * @param threadID the thread ID to use.
+     */
+    Chat(ChatManager chatManager, String participant, String threadID) {
+        this.chatManager = chatManager;
+        this.participant = participant;
+        this.threadID = threadID;
+    }
+
+    /**
+     * Returns the thread id associated with this chat, which corresponds to the
+     * <tt>thread</tt> field of XMPP messages. This method may return <tt>null</tt>
+     * if there is no thread ID is associated with this Chat.
+     *
+     * @return the thread ID of this chat.
+     */
+    public String getThreadID() {
+        return threadID;
+    }
+
+    /**
+     * Returns the name of the user the chat is with.
+     *
+     * @return the name of the user the chat is occuring with.
+     */
+    public String getParticipant() {
+        return participant;
+    }
+
+    /**
+     * Sends the specified text as a message to the other chat participant.
+     * This is a convenience method for:
+     *
+     * <pre>
+     *     Message message = chat.createMessage();
+     *     message.setBody(messageText);
+     *     chat.sendMessage(message);
+     * </pre>
+     *
+     * @param text the text to send.
+     * @throws XMPPException if sending the message fails.
+     */
+    public void sendMessage(String text) throws XMPPException {
+        Message message = new Message(participant, Message.Type.chat);
+        message.setThread(threadID);
+        message.setBody(text);
+        chatManager.sendMessage(this, message);
+    }
+
+    /**
+     * Sends a message to the other chat participant. The thread ID, recipient,
+     * and message type of the message will automatically set to those of this chat.
+     *
+     * @param message the message to send.
+     * @throws XMPPException if an error occurs sending the message.
+     */
+    public void sendMessage(Message message) throws XMPPException {
+        // Force the recipient, message type, and thread ID since the user elected
+        // to send the message through this chat object.
+        message.setTo(participant);
+        message.setType(Message.Type.chat);
+        message.setThread(threadID);
+        chatManager.sendMessage(this, message);
+    }
+
+    /**
+     * Adds a packet listener that will be notified of any new messages in the
+     * chat.
+     *
+     * @param listener a packet listener.
+     */
+    public void addMessageListener(MessageListener listener) {
+        if(listener == null) {
+            return;
+        }
+        // TODO these references should be weak.
+        listeners.add(listener);
+    }
+
+    public void removeMessageListener(MessageListener listener) {
+        listeners.remove(listener);
+    }
+
+    /**
+     * Returns an unmodifiable collection of all of the listeners registered with this chat.
+     *
+     * @return an unmodifiable collection of all of the listeners registered with this chat.
+     */
+    public Collection<MessageListener> getListeners() {
+        return Collections.unmodifiableCollection(listeners);
+    }
+
+    /**
+     * Creates a {@link org.jivesoftware.smack.PacketCollector} which will accumulate the Messages
+     * for this chat. Always cancel PacketCollectors when finished with them as they will accumulate
+     * messages indefinitely.
+     *
+     * @return the PacketCollector which returns Messages for this chat.
+     */
+    public PacketCollector createCollector() {
+        return chatManager.createPacketCollector(this);
+    }
+
+    /**
+     * Delivers a message directly to this chat, which will add the message
+     * to the collector and deliver it to all listeners registered with the
+     * Chat. This is used by the Connection class to deliver messages
+     * without a thread ID.
+     *
+     * @param message the message.
+     */
+    void deliver(Message message) {
+        // Because the collector and listeners are expecting a thread ID with
+        // a specific value, set the thread ID on the message even though it
+        // probably never had one.
+        message.setThread(threadID);
+
+        for (MessageListener listener : listeners) {
+            listener.processMessage(this, message);
+        }
+    }
+
+
+    @Override
+    public boolean equals(Object obj) {
+        return obj instanceof Chat
+                && threadID.equals(((Chat)obj).getThreadID())
+                && participant.equals(((Chat)obj).getParticipant());
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/ChatManager.java b/src/org/jivesoftware/smack/ChatManager.java
new file mode 100644
index 0000000..22dc3f9
--- /dev/null
+++ b/src/org/jivesoftware/smack/ChatManager.java
@@ -0,0 +1,284 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Map;
+import java.util.Set;
+import java.util.WeakHashMap;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.FromContainsFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.ThreadFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smack.util.collections.ReferenceMap;
+
+import java.util.*;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+/**
+ * The chat manager keeps track of references to all current chats. It will not hold any references
+ * in memory on its own so it is neccesary to keep a reference to the chat object itself. To be
+ * made aware of new chats, register a listener by calling {@link #addChatListener(ChatManagerListener)}.
+ *
+ * @author Alexander Wenckus
+ */
+public class ChatManager {
+
+    /**
+     * Returns the next unique id. Each id made up of a short alphanumeric
+     * prefix along with a unique numeric value.
+     *
+     * @return the next id.
+     */
+    private static synchronized String nextID() {
+        return prefix + Long.toString(id++);
+    }
+
+    /**
+     * A prefix helps to make sure that ID's are unique across mutliple instances.
+     */
+    private static String prefix = StringUtils.randomString(5);
+
+    /**
+     * Keeps track of the current increment, which is appended to the prefix to
+     * forum a unique ID.
+     */
+    private static long id = 0;
+
+    /**
+     * Maps thread ID to chat.
+     */
+    private Map<String, Chat> threadChats = Collections.synchronizedMap(new ReferenceMap<String, Chat>(ReferenceMap.HARD,
+            ReferenceMap.WEAK));
+
+    /**
+     * Maps jids to chats
+     */
+    private Map<String, Chat> jidChats = Collections.synchronizedMap(new ReferenceMap<String, Chat>(ReferenceMap.HARD,
+            ReferenceMap.WEAK));
+
+    /**
+     * Maps base jids to chats
+     */
+    private Map<String, Chat> baseJidChats = Collections.synchronizedMap(new ReferenceMap<String, Chat>(ReferenceMap.HARD,
+	    ReferenceMap.WEAK));
+
+    private Set<ChatManagerListener> chatManagerListeners
+            = new CopyOnWriteArraySet<ChatManagerListener>();
+
+    private Map<PacketInterceptor, PacketFilter> interceptors
+            = new WeakHashMap<PacketInterceptor, PacketFilter>();
+
+    private Connection connection;
+
+    ChatManager(Connection connection) {
+        this.connection = connection;
+
+        PacketFilter filter = new PacketFilter() {
+            public boolean accept(Packet packet) {
+                if (!(packet instanceof Message)) {
+                    return false;
+                }
+                Message.Type messageType = ((Message) packet).getType();
+                return messageType != Message.Type.groupchat &&
+                        messageType != Message.Type.headline;
+            }
+        };
+        // Add a listener for all message packets so that we can deliver errant
+        // messages to the best Chat instance available.
+        connection.addPacketListener(new PacketListener() {
+            public void processPacket(Packet packet) {
+                Message message = (Message) packet;
+                Chat chat;
+                if (message.getThread() == null) {
+                	chat = getUserChat(message.getFrom());
+                }
+                else {
+                    chat = getThreadChat(message.getThread());
+                    if (chat == null) {
+                        // Try to locate the chat based on the sender of the message
+                    	chat = getUserChat(message.getFrom());
+                    }
+                }
+
+                if(chat == null) {
+                    chat = createChat(message);
+                }
+                deliverMessage(chat, message);
+            }
+        }, filter);
+    }
+
+    /**
+     * Creates a new chat and returns it.
+     *
+     * @param userJID the user this chat is with.
+     * @param listener the listener which will listen for new messages from this chat.
+     * @return the created chat.
+     */
+    public Chat createChat(String userJID, MessageListener listener) {
+        String threadID;
+        do  {
+            threadID = nextID();
+        } while (threadChats.get(threadID) != null);
+
+        return createChat(userJID, threadID, listener);
+    }
+
+    /**
+     * Creates a new chat using the specified thread ID, then returns it.
+     * 
+     * @param userJID the jid of the user this chat is with
+     * @param thread the thread of the created chat.
+     * @param listener the listener to add to the chat
+     * @return the created chat.
+     */
+    public Chat createChat(String userJID, String thread, MessageListener listener) {
+        if(thread == null) {
+            thread = nextID();
+        }
+        Chat chat = threadChats.get(thread);
+        if(chat != null) {
+            throw new IllegalArgumentException("ThreadID is already used");
+        }
+        chat = createChat(userJID, thread, true);
+        chat.addMessageListener(listener);
+        return chat;
+    }
+
+    private Chat createChat(String userJID, String threadID, boolean createdLocally) {
+        Chat chat = new Chat(this, userJID, threadID);
+        threadChats.put(threadID, chat);
+        jidChats.put(userJID, chat);
+        baseJidChats.put(StringUtils.parseBareAddress(userJID), chat);
+
+        for(ChatManagerListener listener : chatManagerListeners) {
+            listener.chatCreated(chat, createdLocally);
+        }
+
+        return chat;
+    }
+
+    private Chat createChat(Message message) {
+        String threadID = message.getThread();
+        if(threadID == null) {
+            threadID = nextID();
+        }
+        String userJID = message.getFrom();
+
+        return createChat(userJID, threadID, false);
+    }
+
+    /**
+     * Try to get a matching chat for the given user JID.  Try the full
+     * JID map first, the try to match on the base JID if no match is
+     * found.
+     * 
+     * @param userJID
+     * @return
+     */
+    private Chat getUserChat(String userJID) {
+	Chat match = jidChats.get(userJID);
+	
+	if (match == null) {
+	    match = baseJidChats.get(StringUtils.parseBareAddress(userJID));
+	}
+	return match;
+    }
+
+    public Chat getThreadChat(String thread) {
+        return threadChats.get(thread);
+    }
+
+    /**
+     * Register a new listener with the ChatManager to recieve events related to chats.
+     *
+     * @param listener the listener.
+     */
+    public void addChatListener(ChatManagerListener listener) {
+        chatManagerListeners.add(listener);
+    }
+
+    /**
+     * Removes a listener, it will no longer be notified of new events related to chats.
+     *
+     * @param listener the listener that is being removed
+     */
+    public void removeChatListener(ChatManagerListener listener) {
+        chatManagerListeners.remove(listener);
+    }
+
+    /**
+     * Returns an unmodifiable collection of all chat listeners currently registered with this
+     * manager.
+     *
+     * @return an unmodifiable collection of all chat listeners currently registered with this
+     * manager.
+     */
+    public Collection<ChatManagerListener> getChatListeners() {
+        return Collections.unmodifiableCollection(chatManagerListeners);
+    }
+
+    private void deliverMessage(Chat chat, Message message) {
+        // Here we will run any interceptors
+        chat.deliver(message);
+    }
+
+    void sendMessage(Chat chat, Message message) {
+        for(Map.Entry<PacketInterceptor, PacketFilter> interceptor : interceptors.entrySet()) {
+            PacketFilter filter = interceptor.getValue();
+            if(filter != null && filter.accept(message)) {
+                interceptor.getKey().interceptPacket(message);
+            }
+        }
+        // Ensure that messages being sent have a proper FROM value
+        if (message.getFrom() == null) {
+            message.setFrom(connection.getUser());
+        }
+        connection.sendPacket(message);
+    }
+
+    PacketCollector createPacketCollector(Chat chat) {
+        return connection.createPacketCollector(new AndFilter(new ThreadFilter(chat.getThreadID()), 
+                new FromContainsFilter(chat.getParticipant())));
+    }
+
+    /**
+     * Adds an interceptor which intercepts any messages sent through chats.
+     *
+     * @param packetInterceptor the interceptor.
+     */
+    public void addOutgoingMessageInterceptor(PacketInterceptor packetInterceptor) {
+        addOutgoingMessageInterceptor(packetInterceptor, null);
+    }
+
+    public void addOutgoingMessageInterceptor(PacketInterceptor packetInterceptor, PacketFilter filter) {
+        if (packetInterceptor != null) {
+            interceptors.put(packetInterceptor, filter);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/ChatManagerListener.java b/src/org/jivesoftware/smack/ChatManagerListener.java
new file mode 100644
index 0000000..d7d5ab7
--- /dev/null
+++ b/src/org/jivesoftware/smack/ChatManagerListener.java
@@ -0,0 +1,37 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+/**
+ * A listener for chat related events.
+ *
+ * @author Alexander Wenckus
+ */
+public interface ChatManagerListener {
+
+    /**
+     * Event fired when a new chat is created.
+     *
+     * @param chat the chat that was created.
+     * @param createdLocally true if the chat was created by the local user and false if it wasn't.
+     */
+    void chatCreated(Chat chat, boolean createdLocally);
+}
diff --git a/src/org/jivesoftware/smack/Connection.java b/src/org/jivesoftware/smack/Connection.java
new file mode 100644
index 0000000..c6b4b1c
--- /dev/null
+++ b/src/org/jivesoftware/smack/Connection.java
@@ -0,0 +1,920 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.io.Reader;
+import java.io.Writer;
+import java.lang.reflect.Constructor;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.CopyOnWriteArraySet;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import org.jivesoftware.smack.compression.JzlibInputOutputStream;
+import org.jivesoftware.smack.compression.XMPPInputOutputStream;
+import org.jivesoftware.smack.compression.Java7ZlibInputOutputStream;
+import org.jivesoftware.smack.debugger.SmackDebugger;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+
+/**
+ * The abstract Connection class provides an interface for connections to a
+ * XMPP server and implements shared methods which are used by the
+ * different types of connections (e.g. XMPPConnection or BoshConnection).
+ * 
+ * To create a connection to a XMPP server a simple usage of this API might
+ * look like the following:
+ * <pre>
+ * // Create a connection to the igniterealtime.org XMPP server.
+ * Connection con = new XMPPConnection("igniterealtime.org");
+ * // Connect to the server
+ * con.connect();
+ * // Most servers require you to login before performing other tasks.
+ * con.login("jsmith", "mypass");
+ * // Start a new conversation with John Doe and send him a message.
+ * Chat chat = connection.getChatManager().createChat("jdoe@igniterealtime.org"</font>, new MessageListener() {
+ * <p/>
+ *     public void processMessage(Chat chat, Message message) {
+ *         // Print out any messages we get back to standard out.
+ *         System.out.println(<font color="green">"Received message: "</font> + message);
+ *     }
+ * });
+ * chat.sendMessage(<font color="green">"Howdy!"</font>);
+ * // Disconnect from the server
+ * con.disconnect();
+ * </pre>
+ * <p/>
+ * Connections can be reused between connections. This means that an Connection
+ * may be connected, disconnected and then connected again. Listeners of the Connection
+ * will be retained accross connections.<p>
+ * <p/>
+ * If a connected Connection gets disconnected abruptly then it will try to reconnect
+ * again. To stop the reconnection process, use {@link #disconnect()}. Once stopped
+ * you can use {@link #connect()} to manually connect to the server.
+ * 
+ * @see XMPPConnection
+ * @author Matt Tucker
+ * @author Guenther Niess
+ */
+public abstract class Connection {
+
+    /** 
+     * Counter to uniquely identify connections that are created.
+     */
+    private final static AtomicInteger connectionCounter = new AtomicInteger(0);
+
+    /**
+     * A set of listeners which will be invoked if a new connection is created.
+     */
+    private final static Set<ConnectionCreationListener> connectionEstablishedListeners =
+            new CopyOnWriteArraySet<ConnectionCreationListener>();
+
+    protected final static List<XMPPInputOutputStream> compressionHandlers = new ArrayList<XMPPInputOutputStream>(2);
+
+    /**
+     * Value that indicates whether debugging is enabled. When enabled, a debug
+     * window will apear for each new connection that will contain the following
+     * information:<ul>
+     * <li> Client Traffic -- raw XML traffic generated by Smack and sent to the server.
+     * <li> Server Traffic -- raw XML traffic sent by the server to the client.
+     * <li> Interpreted Packets -- shows XML packets from the server as parsed by Smack.
+     * </ul>
+     * <p/>
+     * Debugging can be enabled by setting this field to true, or by setting the Java system
+     * property <tt>smack.debugEnabled</tt> to true. The system property can be set on the
+     * command line such as "java SomeApp -Dsmack.debugEnabled=true".
+     */
+    public static boolean DEBUG_ENABLED = false;
+
+    static {
+        // Use try block since we may not have permission to get a system
+        // property (for example, when an applet).
+        try {
+            DEBUG_ENABLED = Boolean.getBoolean("smack.debugEnabled");
+        }
+        catch (Exception e) {
+            // Ignore.
+        }
+        // Ensure the SmackConfiguration class is loaded by calling a method in it.
+        SmackConfiguration.getVersion();
+        // Add the Java7 compression handler first, since it's preferred
+        compressionHandlers.add(new Java7ZlibInputOutputStream());
+        // If we don't have access to the Java7 API use the JZlib compression handler
+        compressionHandlers.add(new JzlibInputOutputStream());
+    }
+
+    /**
+     * A collection of ConnectionListeners which listen for connection closing
+     * and reconnection events.
+     */
+    protected final Collection<ConnectionListener> connectionListeners =
+            new CopyOnWriteArrayList<ConnectionListener>();
+
+    /**
+     * A collection of PacketCollectors which collects packets for a specified filter
+     * and perform blocking and polling operations on the result queue.
+     */
+    protected final Collection<PacketCollector> collectors = new ConcurrentLinkedQueue<PacketCollector>();
+
+    /**
+     * List of PacketListeners that will be notified when a new packet was received.
+     */
+    protected final Map<PacketListener, ListenerWrapper> recvListeners =
+            new ConcurrentHashMap<PacketListener, ListenerWrapper>();
+
+    /**
+     * List of PacketListeners that will be notified when a new packet was sent.
+     */
+    protected final Map<PacketListener, ListenerWrapper> sendListeners =
+            new ConcurrentHashMap<PacketListener, ListenerWrapper>();
+
+    /**
+     * List of PacketInterceptors that will be notified when a new packet is about to be
+     * sent to the server. These interceptors may modify the packet before it is being
+     * actually sent to the server.
+     */
+    protected final Map<PacketInterceptor, InterceptorWrapper> interceptors =
+            new ConcurrentHashMap<PacketInterceptor, InterceptorWrapper>();
+
+    /**
+     * The AccountManager allows creation and management of accounts on an XMPP server.
+     */
+    private AccountManager accountManager = null;
+
+    /**
+     * The ChatManager keeps track of references to all current chats.
+     */
+    protected ChatManager chatManager = null;
+
+    /**
+     * The SmackDebugger allows to log and debug XML traffic.
+     */
+    protected SmackDebugger debugger = null;
+
+    /**
+     * The Reader which is used for the {@see debugger}.
+     */
+    protected Reader reader;
+
+    /**
+     * The Writer which is used for the {@see debugger}.
+     */
+    protected Writer writer;
+    
+    /**
+     * The permanent storage for the roster
+     */
+    protected RosterStorage rosterStorage;
+
+
+    /**
+     * The SASLAuthentication manager that is responsible for authenticating with the server.
+     */
+    protected SASLAuthentication saslAuthentication = new SASLAuthentication(this);
+
+    /**
+     * A number to uniquely identify connections that are created. This is distinct from the
+     * connection ID, which is a value sent by the server once a connection is made.
+     */
+    protected final int connectionCounterValue = connectionCounter.getAndIncrement();
+
+    /**
+     * Holds the initial configuration used while creating the connection.
+     */
+    protected final ConnectionConfiguration config;
+
+    /**
+     * Holds the Caps Node information for the used XMPP service (i.e. the XMPP server)
+     */
+    private String serviceCapsNode;
+
+    protected XMPPInputOutputStream compressionHandler;
+
+    /**
+     * Create a new Connection to a XMPP server.
+     * 
+     * @param configuration The configuration which is used to establish the connection.
+     */
+    protected Connection(ConnectionConfiguration configuration) {
+        config = configuration;
+    }
+
+    /**
+     * Returns the configuration used to connect to the server.
+     * 
+     * @return the configuration used to connect to the server.
+     */
+    protected ConnectionConfiguration getConfiguration() {
+        return config;
+    }
+
+    /**
+     * Returns the name of the service provided by the XMPP server for this connection.
+     * This is also called XMPP domain of the connected server. After
+     * authenticating with the server the returned value may be different.
+     * 
+     * @return the name of the service provided by the XMPP server.
+     */
+    public String getServiceName() {
+        return config.getServiceName();
+    }
+
+    /**
+     * Returns the host name of the server where the XMPP server is running. This would be the
+     * IP address of the server or a name that may be resolved by a DNS server.
+     * 
+     * @return the host name of the server where the XMPP server is running.
+     */
+    public String getHost() {
+        return config.getHost();
+    }
+
+    /**
+     * Returns the port number of the XMPP server for this connection. The default port
+     * for normal connections is 5222. The default port for SSL connections is 5223.
+     * 
+     * @return the port number of the XMPP server.
+     */
+    public int getPort() {
+        return config.getPort();
+    }
+
+    /**
+     * Returns the full XMPP address of the user that is logged in to the connection or
+     * <tt>null</tt> if not logged in yet. An XMPP address is in the form
+     * username@server/resource.
+     * 
+     * @return the full XMPP address of the user logged in.
+     */
+    public abstract String getUser();
+
+    /**
+     * Returns the connection ID for this connection, which is the value set by the server
+     * when opening a XMPP stream. If the server does not set a connection ID, this value
+     * will be null. This value will be <tt>null</tt> if not connected to the server.
+     * 
+     * @return the ID of this connection returned from the XMPP server or <tt>null</tt> if
+     *      not connected to the server.
+     */
+    public abstract String getConnectionID();
+
+    /**
+     * Returns true if currently connected to the XMPP server.
+     * 
+     * @return true if connected.
+     */
+    public abstract boolean isConnected();
+
+    /**
+     * Returns true if currently authenticated by successfully calling the login method.
+     * 
+     * @return true if authenticated.
+     */
+    public abstract boolean isAuthenticated();
+
+    /**
+     * Returns true if currently authenticated anonymously.
+     * 
+     * @return true if authenticated anonymously.
+     */
+    public abstract boolean isAnonymous();
+
+    /**
+     * Returns true if the connection to the server has successfully negotiated encryption. 
+     * 
+     * @return true if a secure connection to the server.
+     */
+    public abstract boolean isSecureConnection();
+
+    /**
+     * Returns if the reconnection mechanism is allowed to be used. By default
+     * reconnection is allowed.
+     * 
+     * @return true if the reconnection mechanism is allowed to be used.
+     */
+    protected boolean isReconnectionAllowed() {
+        return config.isReconnectionAllowed();
+    }
+
+    /**
+     * Returns true if network traffic is being compressed. When using stream compression network
+     * traffic can be reduced up to 90%. Therefore, stream compression is ideal when using a slow
+     * speed network connection. However, the server will need to use more CPU time in order to
+     * un/compress network data so under high load the server performance might be affected.
+     * 
+     * @return true if network traffic is being compressed.
+     */
+    public abstract boolean isUsingCompression();
+
+    /**
+     * Establishes a connection to the XMPP server and performs an automatic login
+     * only if the previous connection state was logged (authenticated). It basically
+     * creates and maintains a connection to the server.<p>
+     * <p/>
+     * Listeners will be preserved from a previous connection if the reconnection
+     * occurs after an abrupt termination.
+     * 
+     * @throws XMPPException if an error occurs while trying to establish the connection.
+     */
+    public abstract void connect() throws XMPPException;
+
+    /**
+     * Logs in to the server using the strongest authentication mode supported by
+     * the server, then sets presence to available. If the server supports SASL authentication 
+     * then the user will be authenticated using SASL if not Non-SASL authentication will 
+     * be tried. If more than five seconds (default timeout) elapses in each step of the 
+     * authentication process without a response from the server, or if an error occurs, a 
+     * XMPPException will be thrown.<p>
+     * 
+     * Before logging in (i.e. authenticate) to the server the connection must be connected.
+     * 
+     * It is possible to log in without sending an initial available presence by using
+     * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is
+     * not interested in loading its roster upon login then use
+     * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}.
+     * Finally, if you want to not pass a password and instead use a more advanced mechanism
+     * while using SASL then you may be interested in using
+     * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}.
+     * For more advanced login settings see {@link ConnectionConfiguration}.
+     * 
+     * @param username the username.
+     * @param password the password or <tt>null</tt> if using a CallbackHandler.
+     * @throws XMPPException if an error occurs.
+     */
+    public void login(String username, String password) throws XMPPException {
+        login(username, password, "Smack");
+    }
+
+    /**
+     * Logs in to the server using the strongest authentication mode supported by
+     * the server, then sets presence to available. If the server supports SASL authentication 
+     * then the user will be authenticated using SASL if not Non-SASL authentication will 
+     * be tried. If more than five seconds (default timeout) elapses in each step of the 
+     * authentication process without a response from the server, or if an error occurs, a 
+     * XMPPException will be thrown.<p>
+     * 
+     * Before logging in (i.e. authenticate) to the server the connection must be connected.
+     * 
+     * It is possible to log in without sending an initial available presence by using
+     * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is
+     * not interested in loading its roster upon login then use
+     * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}.
+     * Finally, if you want to not pass a password and instead use a more advanced mechanism
+     * while using SASL then you may be interested in using
+     * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}.
+     * For more advanced login settings see {@link ConnectionConfiguration}.
+     * 
+     * @param username the username.
+     * @param password the password or <tt>null</tt> if using a CallbackHandler.
+     * @param resource the resource.
+     * @throws XMPPException if an error occurs.
+     * @throws IllegalStateException if not connected to the server, or already logged in
+     *      to the serrver.
+     */
+    public abstract void login(String username, String password, String resource) throws XMPPException;
+
+    /**
+     * Logs in to the server anonymously. Very few servers are configured to support anonymous
+     * authentication, so it's fairly likely logging in anonymously will fail. If anonymous login
+     * does succeed, your XMPP address will likely be in the form "123ABC@server/789XYZ" or
+     * "server/123ABC" (where "123ABC" and "789XYZ" is a random value generated by the server).
+     * 
+     * @throws XMPPException if an error occurs or anonymous logins are not supported by the server.
+     * @throws IllegalStateException if not connected to the server, or already logged in
+     *      to the serrver.
+     */
+    public abstract void loginAnonymously() throws XMPPException;
+
+    /**
+     * Sends the specified packet to the server.
+     * 
+     * @param packet the packet to send.
+     */
+    public abstract void sendPacket(Packet packet);
+
+    /**
+     * Returns an account manager instance for this connection.
+     * 
+     * @return an account manager for this connection.
+     */
+    public AccountManager getAccountManager() {
+        if (accountManager == null) {
+            accountManager = new AccountManager(this);
+        }
+        return accountManager;
+    }
+
+    /**
+     * Returns a chat manager instance for this connection. The ChatManager manages all incoming and
+     * outgoing chats on the current connection.
+     * 
+     * @return a chat manager instance for this connection.
+     */
+    public synchronized ChatManager getChatManager() {
+        if (this.chatManager == null) {
+            this.chatManager = new ChatManager(this);
+        }
+        return this.chatManager;
+    }
+
+    /**
+     * Returns the roster for the user.
+     * <p>
+     * This method will never return <code>null</code>, instead if the user has not yet logged into
+     * the server or is logged in anonymously all modifying methods of the returned roster object
+     * like {@link Roster#createEntry(String, String, String[])},
+     * {@link Roster#removeEntry(RosterEntry)} , etc. except adding or removing
+     * {@link RosterListener}s will throw an IllegalStateException.
+     * 
+     * @return the user's roster.
+     */
+    public abstract Roster getRoster();
+    
+    /**
+     * Set the store for the roster of this connection. If you set the roster storage
+     * of a connection you enable support for XEP-0237 (RosterVersioning)
+     * @param store the store used for roster versioning
+     * @throws IllegalStateException if you add a roster store when roster is initializied
+     */
+    public abstract void setRosterStorage(RosterStorage storage) throws IllegalStateException;
+    
+    /**
+     * Returns the SASLAuthentication manager that is responsible for authenticating with
+     * the server.
+     * 
+     * @return the SASLAuthentication manager that is responsible for authenticating with
+     *         the server.
+     */
+    public SASLAuthentication getSASLAuthentication() {
+        return saslAuthentication;
+    }
+
+    /**
+     * Closes the connection by setting presence to unavailable then closing the connection to
+     * the XMPP server. The Connection can still be used for connecting to the server
+     * again.<p>
+     * <p/>
+     * This method cleans up all resources used by the connection. Therefore, the roster,
+     * listeners and other stateful objects cannot be re-used by simply calling connect()
+     * on this connection again. This is unlike the behavior during unexpected disconnects
+     * (and subsequent connections). In that case, all state is preserved to allow for
+     * more seamless error recovery.
+     */
+    public void disconnect() {
+        disconnect(new Presence(Presence.Type.unavailable));
+    }
+
+    /**
+     * Closes the connection. A custom unavailable presence is sent to the server, followed
+     * by closing the stream. The Connection can still be used for connecting to the server
+     * again. A custom unavilable presence is useful for communicating offline presence
+     * information such as "On vacation". Typically, just the status text of the presence
+     * packet is set with online information, but most XMPP servers will deliver the full
+     * presence packet with whatever data is set.<p>
+     * <p/>
+     * This method cleans up all resources used by the connection. Therefore, the roster,
+     * listeners and other stateful objects cannot be re-used by simply calling connect()
+     * on this connection again. This is unlike the behavior during unexpected disconnects
+     * (and subsequent connections). In that case, all state is preserved to allow for
+     * more seamless error recovery.
+     * 
+     * @param unavailablePresence the presence packet to send during shutdown.
+     */
+    public abstract void disconnect(Presence unavailablePresence);
+
+    /**
+     * Adds a new listener that will be notified when new Connections are created. Note
+     * that newly created connections will not be actually connected to the server.
+     * 
+     * @param connectionCreationListener a listener interested on new connections.
+     */
+    public static void addConnectionCreationListener(
+            ConnectionCreationListener connectionCreationListener) {
+        connectionEstablishedListeners.add(connectionCreationListener);
+    }
+
+    /**
+     * Removes a listener that was interested in connection creation events.
+     * 
+     * @param connectionCreationListener a listener interested on new connections.
+     */
+    public static void removeConnectionCreationListener(
+            ConnectionCreationListener connectionCreationListener) {
+        connectionEstablishedListeners.remove(connectionCreationListener);
+    }
+
+    /**
+     * Get the collection of listeners that are interested in connection creation events.
+     * 
+     * @return a collection of listeners interested on new connections.
+     */
+    protected static Collection<ConnectionCreationListener> getConnectionCreationListeners() {
+        return Collections.unmodifiableCollection(connectionEstablishedListeners);
+    }
+
+    /**
+     * Adds a connection listener to this connection that will be notified when
+     * the connection closes or fails. The connection needs to already be connected
+     * or otherwise an IllegalStateException will be thrown.
+     * 
+     * @param connectionListener a connection listener.
+     */
+    public void addConnectionListener(ConnectionListener connectionListener) {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (connectionListener == null) {
+            return;
+        }
+        if (!connectionListeners.contains(connectionListener)) {
+            connectionListeners.add(connectionListener);
+        }
+    }
+
+    /**
+     * Removes a connection listener from this connection.
+     * 
+     * @param connectionListener a connection listener.
+     */
+    public void removeConnectionListener(ConnectionListener connectionListener) {
+        connectionListeners.remove(connectionListener);
+    }
+
+    /**
+     * Get the collection of listeners that are interested in connection events.
+     * 
+     * @return a collection of listeners interested on connection events.
+     */
+    protected Collection<ConnectionListener> getConnectionListeners() {
+        return connectionListeners;
+    }
+
+    /**
+     * Creates a new packet collector for this connection. A packet filter determines
+     * which packets will be accumulated by the collector. A PacketCollector is
+     * more suitable to use than a {@link PacketListener} when you need to wait for
+     * a specific result.
+     * 
+     * @param packetFilter the packet filter to use.
+     * @return a new packet collector.
+     */
+    public PacketCollector createPacketCollector(PacketFilter packetFilter) {
+        PacketCollector collector = new PacketCollector(this, packetFilter);
+        // Add the collector to the list of active collectors.
+        collectors.add(collector);
+        return collector;
+    }
+
+    /**
+     * Remove a packet collector of this connection.
+     * 
+     * @param collector a packet collectors which was created for this connection.
+     */
+    protected void removePacketCollector(PacketCollector collector) {
+        collectors.remove(collector);
+    }
+
+    /**
+     * Get the collection of all packet collectors for this connection.
+     * 
+     * @return a collection of packet collectors for this connection.
+     */
+    protected Collection<PacketCollector> getPacketCollectors() {
+        return collectors;
+    }
+
+    /**
+     * Registers a packet listener with this connection. A packet filter determines
+     * which packets will be delivered to the listener. If the same packet listener
+     * is added again with a different filter, only the new filter will be used.
+     * 
+     * @param packetListener the packet listener to notify of new received packets.
+     * @param packetFilter   the packet filter to use.
+     */
+    public void addPacketListener(PacketListener packetListener, PacketFilter packetFilter) {
+        if (packetListener == null) {
+            throw new NullPointerException("Packet listener is null.");
+        }
+        ListenerWrapper wrapper = new ListenerWrapper(packetListener, packetFilter);
+        recvListeners.put(packetListener, wrapper);
+    }
+
+    /**
+     * Removes a packet listener for received packets from this connection.
+     * 
+     * @param packetListener the packet listener to remove.
+     */
+    public void removePacketListener(PacketListener packetListener) {
+        recvListeners.remove(packetListener);
+    }
+
+    /**
+     * Get a map of all packet listeners for received packets of this connection.
+     * 
+     * @return a map of all packet listeners for received packets.
+     */
+    protected Map<PacketListener, ListenerWrapper> getPacketListeners() {
+        return recvListeners;
+    }
+
+    /**
+     * Registers a packet listener with this connection. The listener will be
+     * notified of every packet that this connection sends. A packet filter determines
+     * which packets will be delivered to the listener. Note that the thread
+     * that writes packets will be used to invoke the listeners. Therefore, each
+     * packet listener should complete all operations quickly or use a different
+     * thread for processing.
+     * 
+     * @param packetListener the packet listener to notify of sent packets.
+     * @param packetFilter   the packet filter to use.
+     */
+    public void addPacketSendingListener(PacketListener packetListener, PacketFilter packetFilter) {
+        if (packetListener == null) {
+            throw new NullPointerException("Packet listener is null.");
+        }
+        ListenerWrapper wrapper = new ListenerWrapper(packetListener, packetFilter);
+        sendListeners.put(packetListener, wrapper);
+    }
+
+    /**
+     * Removes a packet listener for sending packets from this connection.
+     * 
+     * @param packetListener the packet listener to remove.
+     */
+    public void removePacketSendingListener(PacketListener packetListener) {
+        sendListeners.remove(packetListener);
+    }
+
+    /**
+     * Get a map of all packet listeners for sending packets of this connection.
+     * 
+     * @return a map of all packet listeners for sent packets.
+     */
+    protected Map<PacketListener, ListenerWrapper> getPacketSendingListeners() {
+        return sendListeners;
+    }
+
+
+    /**
+     * Process all packet listeners for sending packets.
+     * 
+     * @param packet the packet to process.
+     */
+    protected void firePacketSendingListeners(Packet packet) {
+        // Notify the listeners of the new sent packet
+        for (ListenerWrapper listenerWrapper : sendListeners.values()) {
+            listenerWrapper.notifyListener(packet);
+        }
+    }
+
+    /**
+     * Registers a packet interceptor with this connection. The interceptor will be
+     * invoked every time a packet is about to be sent by this connection. Interceptors
+     * may modify the packet to be sent. A packet filter determines which packets
+     * will be delivered to the interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to notify of packets about to be sent.
+     * @param packetFilter      the packet filter to use.
+     */
+    public void addPacketInterceptor(PacketInterceptor packetInterceptor,
+            PacketFilter packetFilter) {
+        if (packetInterceptor == null) {
+            throw new NullPointerException("Packet interceptor is null.");
+        }
+        interceptors.put(packetInterceptor, new InterceptorWrapper(packetInterceptor, packetFilter));
+    }
+
+    /**
+     * Removes a packet interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to remove.
+     */
+    public void removePacketInterceptor(PacketInterceptor packetInterceptor) {
+        interceptors.remove(packetInterceptor);
+    }
+    
+    public boolean isSendPresence() {
+        return config.isSendPresence();
+    }
+
+    /**
+     * Get a map of all packet interceptors for sending packets of this connection.
+     * 
+     * @return a map of all packet interceptors for sending packets.
+     */
+    protected Map<PacketInterceptor, InterceptorWrapper> getPacketInterceptors() {
+        return interceptors;
+    }
+
+    /**
+     * Process interceptors. Interceptors may modify the packet that is about to be sent.
+     * Since the thread that requested to send the packet will invoke all interceptors, it
+     * is important that interceptors perform their work as soon as possible so that the
+     * thread does not remain blocked for a long period.
+     * 
+     * @param packet the packet that is going to be sent to the server
+     */
+    protected void firePacketInterceptors(Packet packet) {
+        if (packet != null) {
+            for (InterceptorWrapper interceptorWrapper : interceptors.values()) {
+                interceptorWrapper.notifyListener(packet);
+            }
+        }
+    }
+
+    /**
+     * Initialize the {@link #debugger}. You can specify a customized {@link SmackDebugger}
+     * by setup the system property <code>smack.debuggerClass</code> to the implementation.
+     * 
+     * @throws IllegalStateException if the reader or writer isn't yet initialized.
+     * @throws IllegalArgumentException if the SmackDebugger can't be loaded.
+     */
+    protected void initDebugger() {
+        if (reader == null || writer == null) {
+            throw new NullPointerException("Reader or writer isn't initialized.");
+        }
+        // If debugging is enabled, we open a window and write out all network traffic.
+        if (config.isDebuggerEnabled()) {
+            if (debugger == null) {
+                // Detect the debugger class to use.
+                String className = null;
+                // Use try block since we may not have permission to get a system
+                // property (for example, when an applet).
+                try {
+                    className = System.getProperty("smack.debuggerClass");
+                }
+                catch (Throwable t) {
+                    // Ignore.
+                }
+                Class<?> debuggerClass = null;
+                if (className != null) {
+                    try {
+                        debuggerClass = Class.forName(className);
+                    }
+                    catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                }
+                if (debuggerClass == null) {
+                    try {
+                        debuggerClass =
+                                Class.forName("de.measite.smack.AndroidDebugger");
+                    }
+                    catch (Exception ex) {
+                        try {
+                            debuggerClass =
+                                    Class.forName("org.jivesoftware.smack.debugger.ConsoleDebugger");
+                        }
+                        catch (Exception ex2) {
+                            ex2.printStackTrace();
+                        }
+                    }
+                }
+                // Create a new debugger instance. If an exception occurs then disable the debugging
+                // option
+                try {
+                    Constructor<?> constructor = debuggerClass
+                            .getConstructor(Connection.class, Writer.class, Reader.class);
+                    debugger = (SmackDebugger) constructor.newInstance(this, writer, reader);
+                    reader = debugger.getReader();
+                    writer = debugger.getWriter();
+                }
+                catch (Exception e) {
+                    throw new IllegalArgumentException("Can't initialize the configured debugger!", e);
+                }
+            }
+            else {
+                // Obtain new reader and writer from the existing debugger
+                reader = debugger.newConnectionReader(reader);
+                writer = debugger.newConnectionWriter(writer);
+            }
+        }
+        
+    }
+
+    /**
+     * Set the servers Entity Caps node
+     * 
+     * Connection holds this information in order to avoid a dependency to
+     * smackx where EntityCapsManager lives from smack.
+     * 
+     * @param node
+     */
+    protected void setServiceCapsNode(String node) {
+        serviceCapsNode = node;
+    }
+
+    /**
+     * Retrieve the servers Entity Caps node
+     * 
+     * Connection holds this information in order to avoid a dependency to
+     * smackx where EntityCapsManager lives from smack.
+     * 
+     * @return
+     */
+    public String getServiceCapsNode() {
+        return serviceCapsNode;
+    }
+
+    /**
+     * A wrapper class to associate a packet filter with a listener.
+     */
+    protected static class ListenerWrapper {
+
+        private PacketListener packetListener;
+        private PacketFilter packetFilter;
+
+        /**
+         * Create a class which associates a packet filter with a listener.
+         * 
+         * @param packetListener the packet listener.
+         * @param packetFilter the associated filter or null if it listen for all packets.
+         */
+        public ListenerWrapper(PacketListener packetListener, PacketFilter packetFilter) {
+            this.packetListener = packetListener;
+            this.packetFilter = packetFilter;
+        }
+
+        /**
+         * Notify and process the packet listener if the filter matches the packet.
+         * 
+         * @param packet the packet which was sent or received.
+         */
+        public void notifyListener(Packet packet) {
+            if (packetFilter == null || packetFilter.accept(packet)) {
+                packetListener.processPacket(packet);
+            }
+        }
+    }
+
+    /**
+     * A wrapper class to associate a packet filter with an interceptor.
+     */
+    protected static class InterceptorWrapper {
+
+        private PacketInterceptor packetInterceptor;
+        private PacketFilter packetFilter;
+
+        /**
+         * Create a class which associates a packet filter with an interceptor.
+         * 
+         * @param packetInterceptor the interceptor.
+         * @param packetFilter the associated filter or null if it intercepts all packets.
+         */
+        public InterceptorWrapper(PacketInterceptor packetInterceptor, PacketFilter packetFilter) {
+            this.packetInterceptor = packetInterceptor;
+            this.packetFilter = packetFilter;
+        }
+
+        public boolean equals(Object object) {
+            if (object == null) {
+                return false;
+            }
+            if (object instanceof InterceptorWrapper) {
+                return ((InterceptorWrapper) object).packetInterceptor
+                        .equals(this.packetInterceptor);
+            }
+            else if (object instanceof PacketInterceptor) {
+                return object.equals(this.packetInterceptor);
+            }
+            return false;
+        }
+
+        /**
+         * Notify and process the packet interceptor if the filter matches the packet.
+         * 
+         * @param packet the packet which will be sent.
+         */
+        public void notifyListener(Packet packet) {
+            if (packetFilter == null || packetFilter.accept(packet)) {
+                packetInterceptor.interceptPacket(packet);
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/Connection.java.orig b/src/org/jivesoftware/smack/Connection.java.orig
new file mode 100644
index 0000000..6c70a82
--- /dev/null
+++ b/src/org/jivesoftware/smack/Connection.java.orig
@@ -0,0 +1,920 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.io.Reader;
+import java.io.Writer;
+import java.lang.reflect.Constructor;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.CopyOnWriteArraySet;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import org.jivesoftware.smack.compression.JzlibInputOutputStream;
+import org.jivesoftware.smack.compression.XMPPInputOutputStream;
+import org.jivesoftware.smack.compression.Java7ZlibInputOutputStream;
+import org.jivesoftware.smack.debugger.SmackDebugger;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+
+/**
+ * The abstract Connection class provides an interface for connections to a
+ * XMPP server and implements shared methods which are used by the
+ * different types of connections (e.g. XMPPConnection or BoshConnection).
+ * 
+ * To create a connection to a XMPP server a simple usage of this API might
+ * look like the following:
+ * <pre>
+ * // Create a connection to the igniterealtime.org XMPP server.
+ * Connection con = new XMPPConnection("igniterealtime.org");
+ * // Connect to the server
+ * con.connect();
+ * // Most servers require you to login before performing other tasks.
+ * con.login("jsmith", "mypass");
+ * // Start a new conversation with John Doe and send him a message.
+ * Chat chat = connection.getChatManager().createChat("jdoe@igniterealtime.org"</font>, new MessageListener() {
+ * <p/>
+ *     public void processMessage(Chat chat, Message message) {
+ *         // Print out any messages we get back to standard out.
+ *         System.out.println(<font color="green">"Received message: "</font> + message);
+ *     }
+ * });
+ * chat.sendMessage(<font color="green">"Howdy!"</font>);
+ * // Disconnect from the server
+ * con.disconnect();
+ * </pre>
+ * <p/>
+ * Connections can be reused between connections. This means that an Connection
+ * may be connected, disconnected and then connected again. Listeners of the Connection
+ * will be retained accross connections.<p>
+ * <p/>
+ * If a connected Connection gets disconnected abruptly then it will try to reconnect
+ * again. To stop the reconnection process, use {@link #disconnect()}. Once stopped
+ * you can use {@link #connect()} to manually connect to the server.
+ * 
+ * @see XMPPConnection
+ * @author Matt Tucker
+ * @author Guenther Niess
+ */
+public abstract class Connection {
+
+    /** 
+     * Counter to uniquely identify connections that are created.
+     */
+    private final static AtomicInteger connectionCounter = new AtomicInteger(0);
+
+    /**
+     * A set of listeners which will be invoked if a new connection is created.
+     */
+    private final static Set<ConnectionCreationListener> connectionEstablishedListeners =
+            new CopyOnWriteArraySet<ConnectionCreationListener>();
+
+    protected final static List<XMPPInputOutputStream> compressionHandlers = new ArrayList<XMPPInputOutputStream>(2);
+
+    /**
+     * Value that indicates whether debugging is enabled. When enabled, a debug
+     * window will apear for each new connection that will contain the following
+     * information:<ul>
+     * <li> Client Traffic -- raw XML traffic generated by Smack and sent to the server.
+     * <li> Server Traffic -- raw XML traffic sent by the server to the client.
+     * <li> Interpreted Packets -- shows XML packets from the server as parsed by Smack.
+     * </ul>
+     * <p/>
+     * Debugging can be enabled by setting this field to true, or by setting the Java system
+     * property <tt>smack.debugEnabled</tt> to true. The system property can be set on the
+     * command line such as "java SomeApp -Dsmack.debugEnabled=true".
+     */
+    public static boolean DEBUG_ENABLED = false;
+
+    static {
+        // Use try block since we may not have permission to get a system
+        // property (for example, when an applet).
+        try {
+            DEBUG_ENABLED = Boolean.getBoolean("smack.debugEnabled");
+        }
+        catch (Exception e) {
+            // Ignore.
+        }
+        // Ensure the SmackConfiguration class is loaded by calling a method in it.
+        SmackConfiguration.getVersion();
+        // Add the Java7 compression handler first, since it's preferred
+        compressionHandlers.add(new Java7ZlibInputOutputStream());
+        // If we don't have access to the Java7 API use the JZlib compression handler
+        compressionHandlers.add(new JzlibInputOutputStream());
+    }
+
+    /**
+     * A collection of ConnectionListeners which listen for connection closing
+     * and reconnection events.
+     */
+    protected final Collection<ConnectionListener> connectionListeners =
+            new CopyOnWriteArrayList<ConnectionListener>();
+
+    /**
+     * A collection of PacketCollectors which collects packets for a specified filter
+     * and perform blocking and polling operations on the result queue.
+     */
+    protected final Collection<PacketCollector> collectors = new ConcurrentLinkedQueue<PacketCollector>();
+
+    /**
+     * List of PacketListeners that will be notified when a new packet was received.
+     */
+    protected final Map<PacketListener, ListenerWrapper> recvListeners =
+            new ConcurrentHashMap<PacketListener, ListenerWrapper>();
+
+    /**
+     * List of PacketListeners that will be notified when a new packet was sent.
+     */
+    protected final Map<PacketListener, ListenerWrapper> sendListeners =
+            new ConcurrentHashMap<PacketListener, ListenerWrapper>();
+
+    /**
+     * List of PacketInterceptors that will be notified when a new packet is about to be
+     * sent to the server. These interceptors may modify the packet before it is being
+     * actually sent to the server.
+     */
+    protected final Map<PacketInterceptor, InterceptorWrapper> interceptors =
+            new ConcurrentHashMap<PacketInterceptor, InterceptorWrapper>();
+
+    /**
+     * The AccountManager allows creation and management of accounts on an XMPP server.
+     */
+    private AccountManager accountManager = null;
+
+    /**
+     * The ChatManager keeps track of references to all current chats.
+     */
+    protected ChatManager chatManager = null;
+
+    /**
+     * The SmackDebugger allows to log and debug XML traffic.
+     */
+    protected SmackDebugger debugger = null;
+
+    /**
+     * The Reader which is used for the {@see debugger}.
+     */
+    protected Reader reader;
+
+    /**
+     * The Writer which is used for the {@see debugger}.
+     */
+    protected Writer writer;
+    
+    /**
+     * The permanent storage for the roster
+     */
+    protected RosterStorage rosterStorage;
+
+
+    /**
+     * The SASLAuthentication manager that is responsible for authenticating with the server.
+     */
+    protected SASLAuthentication saslAuthentication = new SASLAuthentication(this);
+
+    /**
+     * A number to uniquely identify connections that are created. This is distinct from the
+     * connection ID, which is a value sent by the server once a connection is made.
+     */
+    protected final int connectionCounterValue = connectionCounter.getAndIncrement();
+
+    /**
+     * Holds the initial configuration used while creating the connection.
+     */
+    protected final ConnectionConfiguration config;
+
+    /**
+     * Holds the Caps Node information for the used XMPP service (i.e. the XMPP server)
+     */
+    private String serviceCapsNode;
+
+    protected XMPPInputOutputStream compressionHandler;
+
+    /**
+     * Create a new Connection to a XMPP server.
+     * 
+     * @param configuration The configuration which is used to establish the connection.
+     */
+    protected Connection(ConnectionConfiguration configuration) {
+        config = configuration;
+    }
+
+    /**
+     * Returns the configuration used to connect to the server.
+     * 
+     * @return the configuration used to connect to the server.
+     */
+    protected ConnectionConfiguration getConfiguration() {
+        return config;
+    }
+
+    /**
+     * Returns the name of the service provided by the XMPP server for this connection.
+     * This is also called XMPP domain of the connected server. After
+     * authenticating with the server the returned value may be different.
+     * 
+     * @return the name of the service provided by the XMPP server.
+     */
+    public String getServiceName() {
+        return config.getServiceName();
+    }
+
+    /**
+     * Returns the host name of the server where the XMPP server is running. This would be the
+     * IP address of the server or a name that may be resolved by a DNS server.
+     * 
+     * @return the host name of the server where the XMPP server is running.
+     */
+    public String getHost() {
+        return config.getHost();
+    }
+
+    /**
+     * Returns the port number of the XMPP server for this connection. The default port
+     * for normal connections is 5222. The default port for SSL connections is 5223.
+     * 
+     * @return the port number of the XMPP server.
+     */
+    public int getPort() {
+        return config.getPort();
+    }
+
+    /**
+     * Returns the full XMPP address of the user that is logged in to the connection or
+     * <tt>null</tt> if not logged in yet. An XMPP address is in the form
+     * username@server/resource.
+     * 
+     * @return the full XMPP address of the user logged in.
+     */
+    public abstract String getUser();
+
+    /**
+     * Returns the connection ID for this connection, which is the value set by the server
+     * when opening a XMPP stream. If the server does not set a connection ID, this value
+     * will be null. This value will be <tt>null</tt> if not connected to the server.
+     * 
+     * @return the ID of this connection returned from the XMPP server or <tt>null</tt> if
+     *      not connected to the server.
+     */
+    public abstract String getConnectionID();
+
+    /**
+     * Returns true if currently connected to the XMPP server.
+     * 
+     * @return true if connected.
+     */
+    public abstract boolean isConnected();
+
+    /**
+     * Returns true if currently authenticated by successfully calling the login method.
+     * 
+     * @return true if authenticated.
+     */
+    public abstract boolean isAuthenticated();
+
+    /**
+     * Returns true if currently authenticated anonymously.
+     * 
+     * @return true if authenticated anonymously.
+     */
+    public abstract boolean isAnonymous();
+
+    /**
+     * Returns true if the connection to the server has successfully negotiated encryption. 
+     * 
+     * @return true if a secure connection to the server.
+     */
+    public abstract boolean isSecureConnection();
+
+    /**
+     * Returns if the reconnection mechanism is allowed to be used. By default
+     * reconnection is allowed.
+     * 
+     * @return true if the reconnection mechanism is allowed to be used.
+     */
+    protected boolean isReconnectionAllowed() {
+        return config.isReconnectionAllowed();
+    }
+
+    /**
+     * Returns true if network traffic is being compressed. When using stream compression network
+     * traffic can be reduced up to 90%. Therefore, stream compression is ideal when using a slow
+     * speed network connection. However, the server will need to use more CPU time in order to
+     * un/compress network data so under high load the server performance might be affected.
+     * 
+     * @return true if network traffic is being compressed.
+     */
+    public abstract boolean isUsingCompression();
+
+    /**
+     * Establishes a connection to the XMPP server and performs an automatic login
+     * only if the previous connection state was logged (authenticated). It basically
+     * creates and maintains a connection to the server.<p>
+     * <p/>
+     * Listeners will be preserved from a previous connection if the reconnection
+     * occurs after an abrupt termination.
+     * 
+     * @throws XMPPException if an error occurs while trying to establish the connection.
+     */
+    public abstract void connect() throws XMPPException;
+
+    /**
+     * Logs in to the server using the strongest authentication mode supported by
+     * the server, then sets presence to available. If the server supports SASL authentication 
+     * then the user will be authenticated using SASL if not Non-SASL authentication will 
+     * be tried. If more than five seconds (default timeout) elapses in each step of the 
+     * authentication process without a response from the server, or if an error occurs, a 
+     * XMPPException will be thrown.<p>
+     * 
+     * Before logging in (i.e. authenticate) to the server the connection must be connected.
+     * 
+     * It is possible to log in without sending an initial available presence by using
+     * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is
+     * not interested in loading its roster upon login then use
+     * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}.
+     * Finally, if you want to not pass a password and instead use a more advanced mechanism
+     * while using SASL then you may be interested in using
+     * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}.
+     * For more advanced login settings see {@link ConnectionConfiguration}.
+     * 
+     * @param username the username.
+     * @param password the password or <tt>null</tt> if using a CallbackHandler.
+     * @throws XMPPException if an error occurs.
+     */
+    public void login(String username, String password) throws XMPPException {
+        login(username, password, "Smack");
+    }
+
+    /**
+     * Logs in to the server using the strongest authentication mode supported by
+     * the server, then sets presence to available. If the server supports SASL authentication 
+     * then the user will be authenticated using SASL if not Non-SASL authentication will 
+     * be tried. If more than five seconds (default timeout) elapses in each step of the 
+     * authentication process without a response from the server, or if an error occurs, a 
+     * XMPPException will be thrown.<p>
+     * 
+     * Before logging in (i.e. authenticate) to the server the connection must be connected.
+     * 
+     * It is possible to log in without sending an initial available presence by using
+     * {@link ConnectionConfiguration#setSendPresence(boolean)}. If this connection is
+     * not interested in loading its roster upon login then use
+     * {@link ConnectionConfiguration#setRosterLoadedAtLogin(boolean)}.
+     * Finally, if you want to not pass a password and instead use a more advanced mechanism
+     * while using SASL then you may be interested in using
+     * {@link ConnectionConfiguration#setCallbackHandler(javax.security.auth.callback.CallbackHandler)}.
+     * For more advanced login settings see {@link ConnectionConfiguration}.
+     * 
+     * @param username the username.
+     * @param password the password or <tt>null</tt> if using a CallbackHandler.
+     * @param resource the resource.
+     * @throws XMPPException if an error occurs.
+     * @throws IllegalStateException if not connected to the server, or already logged in
+     *      to the serrver.
+     */
+    public abstract void login(String username, String password, String resource) throws XMPPException;
+
+    /**
+     * Logs in to the server anonymously. Very few servers are configured to support anonymous
+     * authentication, so it's fairly likely logging in anonymously will fail. If anonymous login
+     * does succeed, your XMPP address will likely be in the form "123ABC@server/789XYZ" or
+     * "server/123ABC" (where "123ABC" and "789XYZ" is a random value generated by the server).
+     * 
+     * @throws XMPPException if an error occurs or anonymous logins are not supported by the server.
+     * @throws IllegalStateException if not connected to the server, or already logged in
+     *      to the serrver.
+     */
+    public abstract void loginAnonymously() throws XMPPException;
+
+    /**
+     * Sends the specified packet to the server.
+     * 
+     * @param packet the packet to send.
+     */
+    public abstract void sendPacket(Packet packet);
+
+    /**
+     * Returns an account manager instance for this connection.
+     * 
+     * @return an account manager for this connection.
+     */
+    public AccountManager getAccountManager() {
+        if (accountManager == null) {
+            accountManager = new AccountManager(this);
+        }
+        return accountManager;
+    }
+
+    /**
+     * Returns a chat manager instance for this connection. The ChatManager manages all incoming and
+     * outgoing chats on the current connection.
+     * 
+     * @return a chat manager instance for this connection.
+     */
+    public synchronized ChatManager getChatManager() {
+        if (this.chatManager == null) {
+            this.chatManager = new ChatManager(this);
+        }
+        return this.chatManager;
+    }
+
+    /**
+     * Returns the roster for the user.
+     * <p>
+     * This method will never return <code>null</code>, instead if the user has not yet logged into
+     * the server or is logged in anonymously all modifying methods of the returned roster object
+     * like {@link Roster#createEntry(String, String, String[])},
+     * {@link Roster#removeEntry(RosterEntry)} , etc. except adding or removing
+     * {@link RosterListener}s will throw an IllegalStateException.
+     * 
+     * @return the user's roster.
+     */
+    public abstract Roster getRoster();
+    
+    /**
+     * Set the store for the roster of this connection. If you set the roster storage
+     * of a connection you enable support for XEP-0237 (RosterVersioning)
+     * @param store the store used for roster versioning
+     * @throws IllegalStateException if you add a roster store when roster is initializied
+     */
+    public abstract void setRosterStorage(RosterStorage storage) throws IllegalStateException;
+    
+    /**
+     * Returns the SASLAuthentication manager that is responsible for authenticating with
+     * the server.
+     * 
+     * @return the SASLAuthentication manager that is responsible for authenticating with
+     *         the server.
+     */
+    public SASLAuthentication getSASLAuthentication() {
+        return saslAuthentication;
+    }
+
+    /**
+     * Closes the connection by setting presence to unavailable then closing the connection to
+     * the XMPP server. The Connection can still be used for connecting to the server
+     * again.<p>
+     * <p/>
+     * This method cleans up all resources used by the connection. Therefore, the roster,
+     * listeners and other stateful objects cannot be re-used by simply calling connect()
+     * on this connection again. This is unlike the behavior during unexpected disconnects
+     * (and subsequent connections). In that case, all state is preserved to allow for
+     * more seamless error recovery.
+     */
+    public void disconnect() {
+        disconnect(new Presence(Presence.Type.unavailable));
+    }
+
+    /**
+     * Closes the connection. A custom unavailable presence is sent to the server, followed
+     * by closing the stream. The Connection can still be used for connecting to the server
+     * again. A custom unavilable presence is useful for communicating offline presence
+     * information such as "On vacation". Typically, just the status text of the presence
+     * packet is set with online information, but most XMPP servers will deliver the full
+     * presence packet with whatever data is set.<p>
+     * <p/>
+     * This method cleans up all resources used by the connection. Therefore, the roster,
+     * listeners and other stateful objects cannot be re-used by simply calling connect()
+     * on this connection again. This is unlike the behavior during unexpected disconnects
+     * (and subsequent connections). In that case, all state is preserved to allow for
+     * more seamless error recovery.
+     * 
+     * @param unavailablePresence the presence packet to send during shutdown.
+     */
+    public abstract void disconnect(Presence unavailablePresence);
+
+    /**
+     * Adds a new listener that will be notified when new Connections are created. Note
+     * that newly created connections will not be actually connected to the server.
+     * 
+     * @param connectionCreationListener a listener interested on new connections.
+     */
+    public static void addConnectionCreationListener(
+            ConnectionCreationListener connectionCreationListener) {
+        connectionEstablishedListeners.add(connectionCreationListener);
+    }
+
+    /**
+     * Removes a listener that was interested in connection creation events.
+     * 
+     * @param connectionCreationListener a listener interested on new connections.
+     */
+    public static void removeConnectionCreationListener(
+            ConnectionCreationListener connectionCreationListener) {
+        connectionEstablishedListeners.remove(connectionCreationListener);
+    }
+
+    /**
+     * Get the collection of listeners that are interested in connection creation events.
+     * 
+     * @return a collection of listeners interested on new connections.
+     */
+    protected static Collection<ConnectionCreationListener> getConnectionCreationListeners() {
+        return Collections.unmodifiableCollection(connectionEstablishedListeners);
+    }
+
+    /**
+     * Adds a connection listener to this connection that will be notified when
+     * the connection closes or fails. The connection needs to already be connected
+     * or otherwise an IllegalStateException will be thrown.
+     * 
+     * @param connectionListener a connection listener.
+     */
+    public void addConnectionListener(ConnectionListener connectionListener) {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (connectionListener == null) {
+            return;
+        }
+        if (!connectionListeners.contains(connectionListener)) {
+            connectionListeners.add(connectionListener);
+        }
+    }
+
+    /**
+     * Removes a connection listener from this connection.
+     * 
+     * @param connectionListener a connection listener.
+     */
+    public void removeConnectionListener(ConnectionListener connectionListener) {
+        connectionListeners.remove(connectionListener);
+    }
+
+    /**
+     * Get the collection of listeners that are interested in connection events.
+     * 
+     * @return a collection of listeners interested on connection events.
+     */
+    protected Collection<ConnectionListener> getConnectionListeners() {
+        return connectionListeners;
+    }
+
+    /**
+     * Creates a new packet collector for this connection. A packet filter determines
+     * which packets will be accumulated by the collector. A PacketCollector is
+     * more suitable to use than a {@link PacketListener} when you need to wait for
+     * a specific result.
+     * 
+     * @param packetFilter the packet filter to use.
+     * @return a new packet collector.
+     */
+    public PacketCollector createPacketCollector(PacketFilter packetFilter) {
+        PacketCollector collector = new PacketCollector(this, packetFilter);
+        // Add the collector to the list of active collectors.
+        collectors.add(collector);
+        return collector;
+    }
+
+    /**
+     * Remove a packet collector of this connection.
+     * 
+     * @param collector a packet collectors which was created for this connection.
+     */
+    protected void removePacketCollector(PacketCollector collector) {
+        collectors.remove(collector);
+    }
+
+    /**
+     * Get the collection of all packet collectors for this connection.
+     * 
+     * @return a collection of packet collectors for this connection.
+     */
+    protected Collection<PacketCollector> getPacketCollectors() {
+        return collectors;
+    }
+
+    /**
+     * Registers a packet listener with this connection. A packet filter determines
+     * which packets will be delivered to the listener. If the same packet listener
+     * is added again with a different filter, only the new filter will be used.
+     * 
+     * @param packetListener the packet listener to notify of new received packets.
+     * @param packetFilter   the packet filter to use.
+     */
+    public void addPacketListener(PacketListener packetListener, PacketFilter packetFilter) {
+        if (packetListener == null) {
+            throw new NullPointerException("Packet listener is null.");
+        }
+        ListenerWrapper wrapper = new ListenerWrapper(packetListener, packetFilter);
+        recvListeners.put(packetListener, wrapper);
+    }
+
+    /**
+     * Removes a packet listener for received packets from this connection.
+     * 
+     * @param packetListener the packet listener to remove.
+     */
+    public void removePacketListener(PacketListener packetListener) {
+        recvListeners.remove(packetListener);
+    }
+
+    /**
+     * Get a map of all packet listeners for received packets of this connection.
+     * 
+     * @return a map of all packet listeners for received packets.
+     */
+    protected Map<PacketListener, ListenerWrapper> getPacketListeners() {
+        return recvListeners;
+    }
+
+    /**
+     * Registers a packet listener with this connection. The listener will be
+     * notified of every packet that this connection sends. A packet filter determines
+     * which packets will be delivered to the listener. Note that the thread
+     * that writes packets will be used to invoke the listeners. Therefore, each
+     * packet listener should complete all operations quickly or use a different
+     * thread for processing.
+     * 
+     * @param packetListener the packet listener to notify of sent packets.
+     * @param packetFilter   the packet filter to use.
+     */
+    public void addPacketSendingListener(PacketListener packetListener, PacketFilter packetFilter) {
+        if (packetListener == null) {
+            throw new NullPointerException("Packet listener is null.");
+        }
+        ListenerWrapper wrapper = new ListenerWrapper(packetListener, packetFilter);
+        sendListeners.put(packetListener, wrapper);
+    }
+
+    /**
+     * Removes a packet listener for sending packets from this connection.
+     * 
+     * @param packetListener the packet listener to remove.
+     */
+    public void removePacketSendingListener(PacketListener packetListener) {
+        sendListeners.remove(packetListener);
+    }
+
+    /**
+     * Get a map of all packet listeners for sending packets of this connection.
+     * 
+     * @return a map of all packet listeners for sent packets.
+     */
+    protected Map<PacketListener, ListenerWrapper> getPacketSendingListeners() {
+        return sendListeners;
+    }
+
+
+    /**
+     * Process all packet listeners for sending packets.
+     * 
+     * @param packet the packet to process.
+     */
+    protected void firePacketSendingListeners(Packet packet) {
+        // Notify the listeners of the new sent packet
+        for (ListenerWrapper listenerWrapper : sendListeners.values()) {
+            listenerWrapper.notifyListener(packet);
+        }
+    }
+
+    /**
+     * Registers a packet interceptor with this connection. The interceptor will be
+     * invoked every time a packet is about to be sent by this connection. Interceptors
+     * may modify the packet to be sent. A packet filter determines which packets
+     * will be delivered to the interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to notify of packets about to be sent.
+     * @param packetFilter      the packet filter to use.
+     */
+    public void addPacketInterceptor(PacketInterceptor packetInterceptor,
+            PacketFilter packetFilter) {
+        if (packetInterceptor == null) {
+            throw new NullPointerException("Packet interceptor is null.");
+        }
+        interceptors.put(packetInterceptor, new InterceptorWrapper(packetInterceptor, packetFilter));
+    }
+
+    /**
+     * Removes a packet interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to remove.
+     */
+    public void removePacketInterceptor(PacketInterceptor packetInterceptor) {
+        interceptors.remove(packetInterceptor);
+    }
+    
+    public boolean isSendPresence() {
+        return config.isSendPresence();
+    }
+
+    /**
+     * Get a map of all packet interceptors for sending packets of this connection.
+     * 
+     * @return a map of all packet interceptors for sending packets.
+     */
+    protected Map<PacketInterceptor, InterceptorWrapper> getPacketInterceptors() {
+        return interceptors;
+    }
+
+    /**
+     * Process interceptors. Interceptors may modify the packet that is about to be sent.
+     * Since the thread that requested to send the packet will invoke all interceptors, it
+     * is important that interceptors perform their work as soon as possible so that the
+     * thread does not remain blocked for a long period.
+     * 
+     * @param packet the packet that is going to be sent to the server
+     */
+    protected void firePacketInterceptors(Packet packet) {
+        if (packet != null) {
+            for (InterceptorWrapper interceptorWrapper : interceptors.values()) {
+                interceptorWrapper.notifyListener(packet);
+            }
+        }
+    }
+
+    /**
+     * Initialize the {@link #debugger}. You can specify a customized {@link SmackDebugger}
+     * by setup the system property <code>smack.debuggerClass</code> to the implementation.
+     * 
+     * @throws IllegalStateException if the reader or writer isn't yet initialized.
+     * @throws IllegalArgumentException if the SmackDebugger can't be loaded.
+     */
+    protected void initDebugger() {
+        if (reader == null || writer == null) {
+            throw new NullPointerException("Reader or writer isn't initialized.");
+        }
+        // If debugging is enabled, we open a window and write out all network traffic.
+        if (config.isDebuggerEnabled()) {
+            if (debugger == null) {
+                // Detect the debugger class to use.
+                String className = null;
+                // Use try block since we may not have permission to get a system
+                // property (for example, when an applet).
+                try {
+                    className = System.getProperty("smack.debuggerClass");
+                }
+                catch (Throwable t) {
+                    // Ignore.
+                }
+                Class<?> debuggerClass = null;
+                if (className != null) {
+                    try {
+                        debuggerClass = Class.forName(className);
+                    }
+                    catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                }
+                if (debuggerClass == null) {
+                    try {
+                        debuggerClass =
+                                Class.forName("org.jivesoftware.smackx.debugger.EnhancedDebugger");
+                    }
+                    catch (Exception ex) {
+                        try {
+                            debuggerClass =
+                                    Class.forName("org.jivesoftware.smack.debugger.LiteDebugger");
+                        }
+                        catch (Exception ex2) {
+                            ex2.printStackTrace();
+                        }
+                    }
+                }
+                // Create a new debugger instance. If an exception occurs then disable the debugging
+                // option
+                try {
+                    Constructor<?> constructor = debuggerClass
+                            .getConstructor(Connection.class, Writer.class, Reader.class);
+                    debugger = (SmackDebugger) constructor.newInstance(this, writer, reader);
+                    reader = debugger.getReader();
+                    writer = debugger.getWriter();
+                }
+                catch (Exception e) {
+                    throw new IllegalArgumentException("Can't initialize the configured debugger!", e);
+                }
+            }
+            else {
+                // Obtain new reader and writer from the existing debugger
+                reader = debugger.newConnectionReader(reader);
+                writer = debugger.newConnectionWriter(writer);
+            }
+        }
+        
+    }
+
+    /**
+     * Set the servers Entity Caps node
+     * 
+     * Connection holds this information in order to avoid a dependency to
+     * smackx where EntityCapsManager lives from smack.
+     * 
+     * @param node
+     */
+    protected void setServiceCapsNode(String node) {
+        serviceCapsNode = node;
+    }
+
+    /**
+     * Retrieve the servers Entity Caps node
+     * 
+     * Connection holds this information in order to avoid a dependency to
+     * smackx where EntityCapsManager lives from smack.
+     * 
+     * @return
+     */
+    public String getServiceCapsNode() {
+        return serviceCapsNode;
+    }
+
+    /**
+     * A wrapper class to associate a packet filter with a listener.
+     */
+    protected static class ListenerWrapper {
+
+        private PacketListener packetListener;
+        private PacketFilter packetFilter;
+
+        /**
+         * Create a class which associates a packet filter with a listener.
+         * 
+         * @param packetListener the packet listener.
+         * @param packetFilter the associated filter or null if it listen for all packets.
+         */
+        public ListenerWrapper(PacketListener packetListener, PacketFilter packetFilter) {
+            this.packetListener = packetListener;
+            this.packetFilter = packetFilter;
+        }
+
+        /**
+         * Notify and process the packet listener if the filter matches the packet.
+         * 
+         * @param packet the packet which was sent or received.
+         */
+        public void notifyListener(Packet packet) {
+            if (packetFilter == null || packetFilter.accept(packet)) {
+                packetListener.processPacket(packet);
+            }
+        }
+    }
+
+    /**
+     * A wrapper class to associate a packet filter with an interceptor.
+     */
+    protected static class InterceptorWrapper {
+
+        private PacketInterceptor packetInterceptor;
+        private PacketFilter packetFilter;
+
+        /**
+         * Create a class which associates a packet filter with an interceptor.
+         * 
+         * @param packetInterceptor the interceptor.
+         * @param packetFilter the associated filter or null if it intercepts all packets.
+         */
+        public InterceptorWrapper(PacketInterceptor packetInterceptor, PacketFilter packetFilter) {
+            this.packetInterceptor = packetInterceptor;
+            this.packetFilter = packetFilter;
+        }
+
+        public boolean equals(Object object) {
+            if (object == null) {
+                return false;
+            }
+            if (object instanceof InterceptorWrapper) {
+                return ((InterceptorWrapper) object).packetInterceptor
+                        .equals(this.packetInterceptor);
+            }
+            else if (object instanceof PacketInterceptor) {
+                return object.equals(this.packetInterceptor);
+            }
+            return false;
+        }
+
+        /**
+         * Notify and process the packet interceptor if the filter matches the packet.
+         * 
+         * @param packet the packet which will be sent.
+         */
+        public void notifyListener(Packet packet) {
+            if (packetFilter == null || packetFilter.accept(packet)) {
+                packetInterceptor.interceptPacket(packet);
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/ConnectionConfiguration.java b/src/org/jivesoftware/smack/ConnectionConfiguration.java
new file mode 100644
index 0000000..d9108d5
--- /dev/null
+++ b/src/org/jivesoftware/smack/ConnectionConfiguration.java
@@ -0,0 +1,787 @@
+/**
+ * $RCSfile$
+ * $Revision: 3306 $
+ * $Date: 2006-01-16 14:34:56 -0300 (Mon, 16 Jan 2006) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.proxy.ProxyInfo;
+import org.jivesoftware.smack.util.DNSUtil;
+import org.jivesoftware.smack.util.dns.HostAddress;
+
+import javax.net.SocketFactory;
+import javax.net.ssl.SSLContext;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import java.io.File;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Configuration to use while establishing the connection to the server. It is possible to
+ * configure the path to the trustore file that keeps the trusted CA root certificates and
+ * enable or disable all or some of the checkings done while verifying server certificates.<p>
+ *
+ * It is also possible to configure if TLS, SASL, and compression are used or not.
+ *
+ * @author Gaston Dombiak
+ */
+public class ConnectionConfiguration implements Cloneable {
+
+    /**
+     * Hostname of the XMPP server. Usually servers use the same service name as the name
+     * of the server. However, there are some servers like google where host would be
+     * talk.google.com and the serviceName would be gmail.com.
+     */
+    private String serviceName;
+
+    private String host;
+    private int port;
+    protected List<HostAddress> hostAddresses;
+
+    private String truststorePath;
+    private String truststoreType;
+    private String truststorePassword;
+    private String keystorePath;
+    private String keystoreType;
+    private String pkcs11Library;
+    private boolean verifyChainEnabled = false;
+    private boolean verifyRootCAEnabled = false;
+    private boolean selfSignedCertificateEnabled = false;
+    private boolean expiredCertificatesCheckEnabled = false;
+    private boolean notMatchingDomainCheckEnabled = false;
+    private boolean isRosterVersioningAvailable = false;
+    private SSLContext customSSLContext;
+
+    private boolean compressionEnabled = false;
+
+    private boolean saslAuthenticationEnabled = true;
+    /**
+     * Used to get information from the user
+     */
+    private CallbackHandler callbackHandler;
+
+    private boolean debuggerEnabled = Connection.DEBUG_ENABLED;
+
+    // Flag that indicates if a reconnection should be attempted when abruptly disconnected
+    private boolean reconnectionAllowed = true;
+    
+    // Holds the socket factory that is used to generate the socket in the connection
+    private SocketFactory socketFactory;
+    
+    // Holds the authentication information for future reconnections
+    private String username;
+    private String password;
+    private String resource;
+    private boolean sendPresence = true;
+    private boolean rosterLoadedAtLogin = true;
+    private SecurityMode securityMode = SecurityMode.enabled;
+	
+	// Holds the proxy information (such as proxyhost, proxyport, username, password etc)
+    protected ProxyInfo proxy;
+
+    /**
+     * Creates a new ConnectionConfiguration for the specified service name.
+     * A DNS SRV lookup will be performed to find out the actual host address
+     * and port to use for the connection.
+     *
+     * @param serviceName the name of the service provided by an XMPP server.
+     */
+    public ConnectionConfiguration(String serviceName) {
+        // Perform DNS lookup to get host and port to use
+        hostAddresses = DNSUtil.resolveXMPPDomain(serviceName);
+        init(serviceName, ProxyInfo.forDefaultProxy());
+    }
+
+    /**
+     * 
+     */
+    protected ConnectionConfiguration() {
+      /* Does nothing */	
+    }
+
+    /**
+     * Creates a new ConnectionConfiguration for the specified service name 
+     * with specified proxy.
+     * A DNS SRV lookup will be performed to find out the actual host address
+     * and port to use for the connection.
+     *
+     * @param serviceName the name of the service provided by an XMPP server.
+     * @param proxy the proxy through which XMPP is to be connected
+     */
+    public ConnectionConfiguration(String serviceName,ProxyInfo proxy) {
+        // Perform DNS lookup to get host and port to use
+        hostAddresses = DNSUtil.resolveXMPPDomain(serviceName);
+        init(serviceName, proxy);
+    }
+
+    /**
+     * Creates a new ConnectionConfiguration using the specified host, port and
+     * service name. This is useful for manually overriding the DNS SRV lookup
+     * process that's used with the {@link #ConnectionConfiguration(String)}
+     * constructor. For example, say that an XMPP server is running at localhost
+     * in an internal network on port 5222 but is configured to think that it's
+     * "example.com" for testing purposes. This constructor is necessary to connect
+     * to the server in that case since a DNS SRV lookup for example.com would not
+     * point to the local testing server.
+     *
+     * @param host the host where the XMPP server is running.
+     * @param port the port where the XMPP is listening.
+     * @param serviceName the name of the service provided by an XMPP server.
+     */
+    public ConnectionConfiguration(String host, int port, String serviceName) {
+        initHostAddresses(host, port);
+        init(serviceName, ProxyInfo.forDefaultProxy());
+    }
+	
+	/**
+     * Creates a new ConnectionConfiguration using the specified host, port and
+     * service name. This is useful for manually overriding the DNS SRV lookup
+     * process that's used with the {@link #ConnectionConfiguration(String)}
+     * constructor. For example, say that an XMPP server is running at localhost
+     * in an internal network on port 5222 but is configured to think that it's
+     * "example.com" for testing purposes. This constructor is necessary to connect
+     * to the server in that case since a DNS SRV lookup for example.com would not
+     * point to the local testing server.
+     *
+     * @param host the host where the XMPP server is running.
+     * @param port the port where the XMPP is listening.
+     * @param serviceName the name of the service provided by an XMPP server.
+     * @param proxy the proxy through which XMPP is to be connected
+     */
+    public ConnectionConfiguration(String host, int port, String serviceName, ProxyInfo proxy) {
+        initHostAddresses(host, port);
+        init(serviceName, proxy);
+    }
+
+    /**
+     * Creates a new ConnectionConfiguration for a connection that will connect
+     * to the desired host and port.
+     *
+     * @param host the host where the XMPP server is running.
+     * @param port the port where the XMPP is listening.
+     */
+    public ConnectionConfiguration(String host, int port) {
+        initHostAddresses(host, port);
+        init(host, ProxyInfo.forDefaultProxy());
+    }
+	
+	/**
+     * Creates a new ConnectionConfiguration for a connection that will connect
+     * to the desired host and port with desired proxy.
+     *
+     * @param host the host where the XMPP server is running.
+     * @param port the port where the XMPP is listening.
+     * @param proxy the proxy through which XMPP is to be connected
+     */
+    public ConnectionConfiguration(String host, int port, ProxyInfo proxy) {
+        initHostAddresses(host, port);
+        init(host, proxy);
+    }
+
+    protected void init(String serviceName, ProxyInfo proxy) {
+        this.serviceName = serviceName;
+        this.proxy = proxy;
+
+        // Build the default path to the cacert truststore file. By default we are
+        // going to use the file located in $JREHOME/lib/security/cacerts.
+        String javaHome = System.getProperty("java.home");
+        StringBuilder buffer = new StringBuilder();
+        buffer.append(javaHome).append(File.separator).append("lib");
+        buffer.append(File.separator).append("security");
+        buffer.append(File.separator).append("cacerts");
+        truststorePath = buffer.toString();
+        // Set the default store type
+        truststoreType = "jks";
+        // Set the default password of the cacert file that is "changeit"
+        truststorePassword = "changeit";
+        keystorePath = System.getProperty("javax.net.ssl.keyStore");
+        keystoreType = "jks";
+        pkcs11Library = "pkcs11.config";
+		
+		//Setting the SocketFactory according to proxy supplied
+        socketFactory = proxy.getSocketFactory();
+    }
+
+    /**
+     * Sets the server name, also known as XMPP domain of the target server.
+     *
+     * @param serviceName the XMPP domain of the target server.
+     */
+    public void setServiceName(String serviceName) {
+        this.serviceName = serviceName;
+    }
+
+    /**
+     * Returns the server name of the target server.
+     *
+     * @return the server name of the target server.
+     */
+    public String getServiceName() {
+        return serviceName;
+    }
+
+    /**
+     * Returns the host to use when establishing the connection. The host and port to use
+     * might have been resolved by a DNS lookup as specified by the XMPP spec (and therefore
+     * may not match the {@link #getServiceName service name}.
+     *
+     * @return the host to use when establishing the connection.
+     */
+    public String getHost() {
+        return host;
+    }
+
+    /**
+     * Returns the port to use when establishing the connection. The host and port to use
+     * might have been resolved by a DNS lookup as specified by the XMPP spec.
+     *
+     * @return the port to use when establishing the connection.
+     */
+    public int getPort() {
+        return port;
+    }
+
+    public void setUsedHostAddress(HostAddress hostAddress) {
+        this.host = hostAddress.getFQDN();
+        this.port = hostAddress.getPort();
+    }
+
+    /**
+     * Returns the TLS security mode used when making the connection. By default,
+     * the mode is {@link SecurityMode#enabled}.
+     *
+     * @return the security mode.
+     */
+    public SecurityMode getSecurityMode() {
+        return securityMode;
+    }
+
+    /**
+     * Sets the TLS security mode used when making the connection. By default,
+     * the mode is {@link SecurityMode#enabled}.
+     *
+     * @param securityMode the security mode.
+     */
+    public void setSecurityMode(SecurityMode securityMode) {
+        this.securityMode = securityMode;
+    }
+
+    /**
+     * Retuns the path to the trust store file. The trust store file contains the root
+     * certificates of several well known CAs. By default, will attempt to use the
+     * the file located in $JREHOME/lib/security/cacerts.
+     *
+     * @return the path to the truststore file.
+     */
+    public String getTruststorePath() {
+        return truststorePath;
+    }
+
+    /**
+     * Sets the path to the trust store file. The truststore file contains the root
+     * certificates of several well?known CAs. By default Smack is going to use
+     * the file located in $JREHOME/lib/security/cacerts.
+     *
+     * @param truststorePath the path to the truststore file.
+     */
+    public void setTruststorePath(String truststorePath) {
+        this.truststorePath = truststorePath;
+    }
+
+    /**
+     * Returns the trust store type, or <tt>null</tt> if it's not set.
+     *
+     * @return the trust store type.
+     */
+    public String getTruststoreType() {
+        return truststoreType;
+    }
+
+    /**
+     * Sets the trust store type.
+     *
+     * @param truststoreType the trust store type.
+     */
+    public void setTruststoreType(String truststoreType) {
+        this.truststoreType = truststoreType;
+    }
+
+    /**
+     * Returns the password to use to access the trust store file. It is assumed that all
+     * certificates share the same password in the trust store.
+     *
+     * @return the password to use to access the truststore file.
+     */
+    public String getTruststorePassword() {
+        return truststorePassword;
+    }
+
+    /**
+     * Sets the password to use to access the trust store file. It is assumed that all
+     * certificates share the same password in the trust store.
+     *
+     * @param truststorePassword the password to use to access the truststore file.
+     */
+    public void setTruststorePassword(String truststorePassword) {
+        this.truststorePassword = truststorePassword;
+    }
+
+    /**
+     * Retuns the path to the keystore file. The key store file contains the 
+     * certificates that may be used to authenticate the client to the server,
+     * in the event the server requests or requires it.
+     *
+     * @return the path to the keystore file.
+     */
+    public String getKeystorePath() {
+        return keystorePath;
+    }
+
+    /**
+     * Sets the path to the keystore file. The key store file contains the 
+     * certificates that may be used to authenticate the client to the server,
+     * in the event the server requests or requires it.
+     *
+     * @param keystorePath the path to the keystore file.
+     */
+    public void setKeystorePath(String keystorePath) {
+        this.keystorePath = keystorePath;
+    }
+
+    /**
+     * Returns the keystore type, or <tt>null</tt> if it's not set.
+     *
+     * @return the keystore type.
+     */
+    public String getKeystoreType() {
+        return keystoreType;
+    }
+
+    /**
+     * Sets the keystore type.
+     *
+     * @param keystoreType the keystore type.
+     */
+    public void setKeystoreType(String keystoreType) {
+        this.keystoreType = keystoreType;
+    }
+
+
+    /**
+     * Returns the PKCS11 library file location, needed when the
+     * Keystore type is PKCS11.
+     *
+     * @return the path to the PKCS11 library file
+     */
+    public String getPKCS11Library() {
+        return pkcs11Library;
+    }
+
+    /**
+     * Sets the PKCS11 library file location, needed when the
+     * Keystore type is PKCS11
+     *
+     * @param pkcs11Library the path to the PKCS11 library file
+     */
+    public void setPKCS11Library(String pkcs11Library) {
+        this.pkcs11Library = pkcs11Library;
+    }
+
+    /**
+     * Returns true if the whole chain of certificates presented by the server are going to
+     * be checked. By default the certificate chain is not verified.
+     *
+     * @return true if the whole chaing of certificates presented by the server are going to
+     *         be checked.
+     */
+    public boolean isVerifyChainEnabled() {
+        return verifyChainEnabled;
+    }
+
+    /**
+     * Sets if the whole chain of certificates presented by the server are going to
+     * be checked. By default the certificate chain is not verified.
+     *
+     * @param verifyChainEnabled if the whole chaing of certificates presented by the server
+     *        are going to be checked.
+     */
+    public void setVerifyChainEnabled(boolean verifyChainEnabled) {
+        this.verifyChainEnabled = verifyChainEnabled;
+    }
+
+    /**
+     * Returns true if root CA checking is going to be done. By default checking is disabled.
+     *
+     * @return true if root CA checking is going to be done.
+     */
+    public boolean isVerifyRootCAEnabled() {
+        return verifyRootCAEnabled;
+    }
+
+    /**
+     * Sets if root CA checking is going to be done. By default checking is disabled.
+     *
+     * @param verifyRootCAEnabled if root CA checking is going to be done.
+     */
+    public void setVerifyRootCAEnabled(boolean verifyRootCAEnabled) {
+        this.verifyRootCAEnabled = verifyRootCAEnabled;
+    }
+
+    /**
+     * Returns true if self-signed certificates are going to be accepted. By default
+     * this option is disabled.
+     *
+     * @return true if self-signed certificates are going to be accepted.
+     */
+    public boolean isSelfSignedCertificateEnabled() {
+        return selfSignedCertificateEnabled;
+    }
+
+    /**
+     * Sets if self-signed certificates are going to be accepted. By default
+     * this option is disabled.
+     *
+     * @param selfSignedCertificateEnabled if self-signed certificates are going to be accepted.
+     */
+    public void setSelfSignedCertificateEnabled(boolean selfSignedCertificateEnabled) {
+        this.selfSignedCertificateEnabled = selfSignedCertificateEnabled;
+    }
+
+    /**
+     * Returns true if certificates presented by the server are going to be checked for their
+     * validity. By default certificates are not verified.
+     *
+     * @return true if certificates presented by the server are going to be checked for their
+     *         validity.
+     */
+    public boolean isExpiredCertificatesCheckEnabled() {
+        return expiredCertificatesCheckEnabled;
+    }
+
+    /**
+     * Sets if certificates presented by the server are going to be checked for their
+     * validity. By default certificates are not verified.
+     *
+     * @param expiredCertificatesCheckEnabled if certificates presented by the server are going
+     *        to be checked for their validity.
+     */
+    public void setExpiredCertificatesCheckEnabled(boolean expiredCertificatesCheckEnabled) {
+        this.expiredCertificatesCheckEnabled = expiredCertificatesCheckEnabled;
+    }
+
+    /**
+     * Returns true if certificates presented by the server are going to be checked for their
+     * domain. By default certificates are not verified.
+     *
+     * @return true if certificates presented by the server are going to be checked for their
+     *         domain.
+     */
+    public boolean isNotMatchingDomainCheckEnabled() {
+        return notMatchingDomainCheckEnabled;
+    }
+
+    /**
+     * Sets if certificates presented by the server are going to be checked for their
+     * domain. By default certificates are not verified.
+     *
+     * @param notMatchingDomainCheckEnabled if certificates presented by the server are going
+     *        to be checked for their domain.
+     */
+    public void setNotMatchingDomainCheckEnabled(boolean notMatchingDomainCheckEnabled) {
+        this.notMatchingDomainCheckEnabled = notMatchingDomainCheckEnabled;
+    }
+
+    /**
+     * Gets the custom SSLContext for SSL sockets. This is null by default.
+     *
+     * @return the SSLContext previously set with setCustomSSLContext() or null.
+     */
+    public SSLContext getCustomSSLContext() {
+        return this.customSSLContext;
+    }
+
+    /**
+     * Sets a custom SSLContext for creating SSL sockets. A custom Context causes all other
+     * SSL/TLS realted settings to be ignored.
+     *
+     * @param context the custom SSLContext for new sockets; null to reset default behavior.
+     */
+    public void setCustomSSLContext(SSLContext context) {
+        this.customSSLContext = context;
+    }
+
+    /**
+     * Returns true if the connection is going to use stream compression. Stream compression
+     * will be requested after TLS was established (if TLS was enabled) and only if the server
+     * offered stream compression. With stream compression network traffic can be reduced
+     * up to 90%. By default compression is disabled.
+     *
+     * @return true if the connection is going to use stream compression.
+     */
+    public boolean isCompressionEnabled() {
+        return compressionEnabled;
+    }
+
+    /**
+     * Sets if the connection is going to use stream compression. Stream compression
+     * will be requested after TLS was established (if TLS was enabled) and only if the server
+     * offered stream compression. With stream compression network traffic can be reduced
+     * up to 90%. By default compression is disabled.
+     *
+     * @param compressionEnabled if the connection is going to use stream compression.
+     */
+    public void setCompressionEnabled(boolean compressionEnabled) {
+        this.compressionEnabled = compressionEnabled;
+    }
+
+    /**
+     * Returns true if the client is going to use SASL authentication when logging into the
+     * server. If SASL authenticatin fails then the client will try to use non-sasl authentication.
+     * By default SASL is enabled.
+     *
+     * @return true if the client is going to use SASL authentication when logging into the
+     *         server.
+     */
+    public boolean isSASLAuthenticationEnabled() {
+        return saslAuthenticationEnabled;
+    }
+
+    /**
+     * Sets whether the client will use SASL authentication when logging into the
+     * server. If SASL authenticatin fails then the client will try to use non-sasl authentication.
+     * By default, SASL is enabled.
+     *
+     * @param saslAuthenticationEnabled if the client is going to use SASL authentication when
+     *        logging into the server.
+     */
+    public void setSASLAuthenticationEnabled(boolean saslAuthenticationEnabled) {
+        this.saslAuthenticationEnabled = saslAuthenticationEnabled;
+    }
+
+    /**
+     * Returns true if the new connection about to be establish is going to be debugged. By
+     * default the value of {@link Connection#DEBUG_ENABLED} is used.
+     *
+     * @return true if the new connection about to be establish is going to be debugged.
+     */
+    public boolean isDebuggerEnabled() {
+        return debuggerEnabled;
+    }
+
+    /**
+     * Sets if the new connection about to be establish is going to be debugged. By
+     * default the value of {@link Connection#DEBUG_ENABLED} is used.
+     *
+     * @param debuggerEnabled if the new connection about to be establish is going to be debugged.
+     */
+    public void setDebuggerEnabled(boolean debuggerEnabled) {
+        this.debuggerEnabled = debuggerEnabled;
+    }
+    
+    /**
+     * Sets if the reconnection mechanism is allowed to be used. By default
+     * reconnection is allowed.
+     * 
+     * @param isAllowed if the reconnection mechanism is allowed to use.
+     */
+    public void setReconnectionAllowed(boolean isAllowed) {
+        this.reconnectionAllowed = isAllowed;
+    }
+    /**
+     * Returns if the reconnection mechanism is allowed to be used. By default
+     * reconnection is allowed.
+     *
+     * @return if the reconnection mechanism is allowed to be used.
+     */
+    public boolean isReconnectionAllowed() {
+        return this.reconnectionAllowed;
+    }
+    
+    /**
+     * Sets the socket factory used to create new xmppConnection sockets.
+     * This is useful when connecting through SOCKS5 proxies.
+     *
+     * @param socketFactory used to create new sockets.
+     */
+    public void setSocketFactory(SocketFactory socketFactory) {
+        this.socketFactory = socketFactory;
+    }
+
+    /**
+     * Sets if an initial available presence will be sent to the server. By default
+     * an available presence will be sent to the server indicating that this presence
+     * is not online and available to receive messages. If you want to log in without
+     * being 'noticed' then pass a <tt>false</tt> value.
+     *
+     * @param sendPresence true if an initial available presence will be sent while logging in.
+     */
+    public void setSendPresence(boolean sendPresence) {
+        this.sendPresence = sendPresence;
+    }
+
+    /**
+     * Returns true if the roster will be loaded from the server when logging in. This
+     * is the common behaviour for clients but sometimes clients may want to differ this
+     * or just never do it if not interested in rosters.
+     *
+     * @return true if the roster will be loaded from the server when logging in.
+     */
+    public boolean isRosterLoadedAtLogin() {
+        return rosterLoadedAtLogin;
+    }
+
+    /**
+     * Sets if the roster will be loaded from the server when logging in. This
+     * is the common behaviour for clients but sometimes clients may want to differ this
+     * or just never do it if not interested in rosters.
+     *
+     * @param rosterLoadedAtLogin if the roster will be loaded from the server when logging in.
+     */
+    public void setRosterLoadedAtLogin(boolean rosterLoadedAtLogin) {
+        this.rosterLoadedAtLogin = rosterLoadedAtLogin;
+    }
+
+    /**
+     * Returns a CallbackHandler to obtain information, such as the password or
+     * principal information during the SASL authentication. A CallbackHandler
+     * will be used <b>ONLY</b> if no password was specified during the login while
+     * using SASL authentication.
+     *
+     * @return a CallbackHandler to obtain information, such as the password or
+     * principal information during the SASL authentication.
+     */
+    public CallbackHandler getCallbackHandler() {
+        return callbackHandler;
+    }
+
+    /**
+     * Sets a CallbackHandler to obtain information, such as the password or
+     * principal information during the SASL authentication. A CallbackHandler
+     * will be used <b>ONLY</b> if no password was specified during the login while
+     * using SASL authentication.
+     *
+     * @param callbackHandler to obtain information, such as the password or
+     * principal information during the SASL authentication.
+     */
+    public void setCallbackHandler(CallbackHandler callbackHandler) {
+        this.callbackHandler = callbackHandler;
+    }
+
+    /**
+     * Returns the socket factory used to create new xmppConnection sockets.
+     * This is useful when connecting through SOCKS5 proxies.
+     * 
+     * @return socketFactory used to create new sockets.
+     */
+    public SocketFactory getSocketFactory() {
+        return this.socketFactory;
+    }
+
+    public List<HostAddress> getHostAddresses() {
+        return Collections.unmodifiableList(hostAddresses);
+    }
+
+    /**
+     * An enumeration for TLS security modes that are available when making a connection
+     * to the XMPP server.
+     */
+    public static enum SecurityMode {
+
+        /**
+         * Securirty via TLS encryption is required in order to connect. If the server
+         * does not offer TLS or if the TLS negotiaton fails, the connection to the server
+         * will fail.
+         */
+        required,
+
+        /**
+         * Security via TLS encryption is used whenever it's available. This is the
+         * default setting.
+         */
+        enabled,
+
+        /**
+         * Security via TLS encryption is disabled and only un-encrypted connections will
+         * be used. If only TLS encryption is available from the server, the connection
+         * will fail.
+         */
+        disabled
+    }
+
+    /**
+     * Returns the username to use when trying to reconnect to the server.
+     *
+     * @return the username to use when trying to reconnect to the server.
+     */
+    String getUsername() {
+        return this.username;
+    }
+
+    /**
+     * Returns the password to use when trying to reconnect to the server.
+     *
+     * @return the password to use when trying to reconnect to the server.
+     */
+    String getPassword() {
+        return this.password;
+    }
+
+    /**
+     * Returns the resource to use when trying to reconnect to the server.
+     *
+     * @return the resource to use when trying to reconnect to the server.
+     */
+    String getResource() {
+        return resource;
+    }
+    
+    boolean isRosterVersioningAvailable(){
+    	return isRosterVersioningAvailable;
+    }
+    
+    void setRosterVersioningAvailable(boolean enabled){
+    	isRosterVersioningAvailable = enabled;
+    }
+
+    /**
+     * Returns true if an available presence should be sent when logging in while reconnecting.
+     *
+     * @return true if an available presence should be sent when logging in while reconnecting
+     */
+    boolean isSendPresence() {
+        return sendPresence;
+    }
+
+    void setLoginInfo(String username, String password, String resource) {
+        this.username = username;
+        this.password = password;
+        this.resource = resource;
+    }
+
+    private void initHostAddresses(String host, int port) {
+        hostAddresses = new ArrayList<HostAddress>(1);
+        HostAddress hostAddress;
+        try {
+             hostAddress = new HostAddress(host, port);
+        } catch (Exception e) {
+            throw new IllegalStateException(e);
+        }
+        hostAddresses.add(hostAddress);
+    }
+}
diff --git a/src/org/jivesoftware/smack/ConnectionCreationListener.java b/src/org/jivesoftware/smack/ConnectionCreationListener.java
new file mode 100644
index 0000000..7cbda18
--- /dev/null
+++ b/src/org/jivesoftware/smack/ConnectionCreationListener.java
@@ -0,0 +1,41 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+/**
+ * Implementors of this interface will be notified when a new {@link Connection}
+ * has been created. The newly created connection will not be actually connected to
+ * the server. Use {@link Connection#addConnectionCreationListener(ConnectionCreationListener)}
+ * to add new listeners.
+ *
+ * @author Gaston Dombiak
+ */
+public interface ConnectionCreationListener {
+
+    /**
+     * Notification that a new connection has been created. The new connection
+     * will not yet be connected to the server.
+     * 
+     * @param connection the newly created connection.
+     */
+    public void connectionCreated(Connection connection);
+
+}
diff --git a/src/org/jivesoftware/smack/ConnectionListener.java b/src/org/jivesoftware/smack/ConnectionListener.java
new file mode 100644
index 0000000..a7ceef1
--- /dev/null
+++ b/src/org/jivesoftware/smack/ConnectionListener.java
@@ -0,0 +1,69 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+/**
+ * Interface that allows for implementing classes to listen for connection closing
+ * and reconnection events. Listeners are registered with Connection objects.
+ *
+ * @see Connection#addConnectionListener
+ * @see Connection#removeConnectionListener
+ * 
+ * @author Matt Tucker
+ */
+public interface ConnectionListener {
+
+    /**
+     * Notification that the connection was closed normally or that the reconnection
+     * process has been aborted.
+     */
+    public void connectionClosed();
+
+    /**
+     * Notification that the connection was closed due to an exception. When
+     * abruptly disconnected it is possible for the connection to try reconnecting
+     * to the server.
+     *
+     * @param e the exception.
+     */
+    public void connectionClosedOnError(Exception e);
+    
+    /**
+     * The connection will retry to reconnect in the specified number of seconds.
+     * 
+     * @param seconds remaining seconds before attempting a reconnection.
+     */
+    public void reconnectingIn(int seconds);
+    
+    /**
+     * The connection has reconnected successfully to the server. Connections will
+     * reconnect to the server when the previous socket connection was abruptly closed.
+     */
+    public void reconnectionSuccessful();
+    
+    /**
+     * An attempt to connect to the server has failed. The connection will keep trying
+     * reconnecting to the server in a moment.
+     *
+     * @param e the exception that caused the reconnection to fail.
+     */
+    public void reconnectionFailed(Exception e);
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/MessageListener.java b/src/org/jivesoftware/smack/MessageListener.java
new file mode 100644
index 0000000..187c56c
--- /dev/null
+++ b/src/org/jivesoftware/smack/MessageListener.java
@@ -0,0 +1,30 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Message;
+
+/**
+ *
+ */
+public interface MessageListener {
+    void processMessage(Chat chat, Message message);
+}
diff --git a/src/org/jivesoftware/smack/NonSASLAuthentication.java b/src/org/jivesoftware/smack/NonSASLAuthentication.java
new file mode 100644
index 0000000..88b91ce
--- /dev/null
+++ b/src/org/jivesoftware/smack/NonSASLAuthentication.java
@@ -0,0 +1,143 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.Authentication;
+import org.jivesoftware.smack.packet.IQ;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+import org.apache.harmony.javax.security.auth.callback.Callback;
+
+/**
+ * Implementation of JEP-0078: Non-SASL Authentication. Follow the following
+ * <a href=http://www.jabber.org/jeps/jep-0078.html>link</a> to obtain more
+ * information about the JEP.
+ *
+ * @author Gaston Dombiak
+ */
+class NonSASLAuthentication implements UserAuthentication {
+
+    private Connection connection;
+
+    public NonSASLAuthentication(Connection connection) {
+        super();
+        this.connection = connection;
+    }
+
+    public String authenticate(String username, String resource, CallbackHandler cbh) throws XMPPException {
+        //Use the callback handler to determine the password, and continue on.
+        PasswordCallback pcb = new PasswordCallback("Password: ",false);
+        try {
+            cbh.handle(new Callback[]{pcb});
+            return authenticate(username, String.valueOf(pcb.getPassword()),resource);
+        } catch (Exception e) {
+            throw new XMPPException("Unable to determine password.",e);
+        }   
+    }
+
+    public String authenticate(String username, String password, String resource) throws
+            XMPPException {
+        // If we send an authentication packet in "get" mode with just the username,
+        // the server will return the list of authentication protocols it supports.
+        Authentication discoveryAuth = new Authentication();
+        discoveryAuth.setType(IQ.Type.GET);
+        discoveryAuth.setUsername(username);
+
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(discoveryAuth.getPacketID()));
+        // Send the packet
+        connection.sendPacket(discoveryAuth);
+        // Wait up to a certain number of seconds for a response from the server.
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        // Otherwise, no error so continue processing.
+        Authentication authTypes = (Authentication) response;
+        collector.cancel();
+
+        // Now, create the authentication packet we'll send to the server.
+        Authentication auth = new Authentication();
+        auth.setUsername(username);
+
+        // Figure out if we should use digest or plain text authentication.
+        if (authTypes.getDigest() != null) {
+            auth.setDigest(connection.getConnectionID(), password);
+        }
+        else if (authTypes.getPassword() != null) {
+            auth.setPassword(password);
+        }
+        else {
+            throw new XMPPException("Server does not support compatible authentication mechanism.");
+        }
+
+        auth.setResource(resource);
+
+        collector = connection.createPacketCollector(new PacketIDFilter(auth.getPacketID()));
+        // Send the packet.
+        connection.sendPacket(auth);
+        // Wait up to a certain number of seconds for a response from the server.
+        response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        if (response == null) {
+            throw new XMPPException("Authentication failed.");
+        }
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        // We're done with the collector, so explicitly cancel it.
+        collector.cancel();
+
+        return response.getTo();
+    }
+
+    public String authenticateAnonymously() throws XMPPException {
+        // Create the authentication packet we'll send to the server.
+        Authentication auth = new Authentication();
+
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(auth.getPacketID()));
+        // Send the packet.
+        connection.sendPacket(auth);
+        // Wait up to a certain number of seconds for a response from the server.
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        if (response == null) {
+            throw new XMPPException("Anonymous login failed.");
+        }
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        // We're done with the collector, so explicitly cancel it.
+        collector.cancel();
+
+        if (response.getTo() != null) {
+            return response.getTo();
+        }
+        else {
+            return connection.getServiceName() + "/" + ((Authentication) response).getResource();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/OpenTrustManager.java b/src/org/jivesoftware/smack/OpenTrustManager.java
new file mode 100644
index 0000000..61ed8c6
--- /dev/null
+++ b/src/org/jivesoftware/smack/OpenTrustManager.java
@@ -0,0 +1,49 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import javax.net.ssl.X509TrustManager;
+import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+
+/**
+ * Dummy trust manager that trust all certificates presented by the server. This class
+ * is used during old SSL connections.
+ *
+ * @author Gaston Dombiak
+ */
+class OpenTrustManager implements X509TrustManager {
+
+    public OpenTrustManager() {
+    }
+
+    public X509Certificate[] getAcceptedIssuers() {
+        return new X509Certificate[0];
+    }
+
+    public void checkClientTrusted(X509Certificate[] arg0, String arg1)
+            throws CertificateException {
+    }
+
+    public void checkServerTrusted(X509Certificate[] arg0, String arg1)
+            throws CertificateException {
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/PacketCollector.java b/src/org/jivesoftware/smack/PacketCollector.java
new file mode 100644
index 0000000..9b4b4ae
--- /dev/null
+++ b/src/org/jivesoftware/smack/PacketCollector.java
@@ -0,0 +1,160 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.util.concurrent.ArrayBlockingQueue;
+import java.util.concurrent.TimeUnit;
+
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Provides a mechanism to collect packets into a result queue that pass a
+ * specified filter. The collector lets you perform blocking and polling
+ * operations on the result queue. So, a PacketCollector is more suitable to
+ * use than a {@link PacketListener} when you need to wait for a specific
+ * result.<p>
+ *
+ * Each packet collector will queue up a configured number of packets for processing before
+ * older packets are automatically dropped.  The default number is retrieved by 
+ * {@link SmackConfiguration#getPacketCollectorSize()}.
+ *
+ * @see Connection#createPacketCollector(PacketFilter)
+ * @author Matt Tucker
+ */
+public class PacketCollector {
+
+    private PacketFilter packetFilter;
+    private ArrayBlockingQueue<Packet> resultQueue;
+    private Connection connection;
+    private boolean cancelled = false;
+
+    /**
+     * Creates a new packet collector. If the packet filter is <tt>null</tt>, then
+     * all packets will match this collector.
+     *
+     * @param conection the connection the collector is tied to.
+     * @param packetFilter determines which packets will be returned by this collector.
+     */
+    protected PacketCollector(Connection conection, PacketFilter packetFilter) {
+    	this(conection, packetFilter, SmackConfiguration.getPacketCollectorSize());
+    }
+
+    /**
+     * Creates a new packet collector. If the packet filter is <tt>null</tt>, then
+     * all packets will match this collector.
+     *
+     * @param conection the connection the collector is tied to.
+     * @param packetFilter determines which packets will be returned by this collector.
+     * @param maxSize the maximum number of packets that will be stored in the collector.
+     */
+    protected PacketCollector(Connection conection, PacketFilter packetFilter, int maxSize) {
+        this.connection = conection;
+        this.packetFilter = packetFilter;
+        this.resultQueue = new ArrayBlockingQueue<Packet>(maxSize);
+    }
+
+    /**
+     * Explicitly cancels the packet collector so that no more results are
+     * queued up. Once a packet collector has been cancelled, it cannot be
+     * re-enabled. Instead, a new packet collector must be created.
+     */
+    public void cancel() {
+        // If the packet collector has already been cancelled, do nothing.
+        if (!cancelled) {
+            cancelled = true;
+            connection.removePacketCollector(this);
+        }
+    }
+
+    /**
+     * Returns the packet filter associated with this packet collector. The packet
+     * filter is used to determine what packets are queued as results.
+     *
+     * @return the packet filter.
+     */
+    public PacketFilter getPacketFilter() {
+        return packetFilter;
+    }
+
+    /**
+     * Polls to see if a packet is currently available and returns it, or
+     * immediately returns <tt>null</tt> if no packets are currently in the
+     * result queue.
+     *
+     * @return the next packet result, or <tt>null</tt> if there are no more
+     *      results.
+     */
+    public Packet pollResult() {
+    	return resultQueue.poll();
+    }
+
+    /**
+     * Returns the next available packet. The method call will block (not return)
+     * until a packet is available.
+     *
+     * @return the next available packet.
+     */
+    public Packet nextResult() {
+        try {
+			return resultQueue.take();
+		}
+		catch (InterruptedException e) {
+			throw new RuntimeException(e);
+		}
+    }
+
+    /**
+     * Returns the next available packet. The method call will block (not return)
+     * until a packet is available or the <tt>timeout</tt> has elapased. If the
+     * timeout elapses without a result, <tt>null</tt> will be returned.
+     *
+     * @param timeout the amount of time to wait for the next packet (in milleseconds).
+     * @return the next available packet.
+     */
+    public Packet nextResult(long timeout) {
+    	try {
+			return resultQueue.poll(timeout, TimeUnit.MILLISECONDS);
+		}
+		catch (InterruptedException e) {
+			throw new RuntimeException(e);
+		}
+    }
+
+    /**
+     * Processes a packet to see if it meets the criteria for this packet collector.
+     * If so, the packet is added to the result queue.
+     *
+     * @param packet the packet to process.
+     */
+    protected void processPacket(Packet packet) {
+        if (packet == null) {
+            return;
+        }
+        
+        if (packetFilter == null || packetFilter.accept(packet)) {
+        	while (!resultQueue.offer(packet)) {
+        		// Since we know the queue is full, this poll should never actually block.
+        		resultQueue.poll();
+        	}
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/PacketInterceptor.java b/src/org/jivesoftware/smack/PacketInterceptor.java
new file mode 100644
index 0000000..bd89031
--- /dev/null
+++ b/src/org/jivesoftware/smack/PacketInterceptor.java
@@ -0,0 +1,49 @@
+/**
+ * $Revision: 2408 $
+ * $Date: 2004-11-02 20:53:30 -0300 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Provides a mechanism to intercept and modify packets that are going to be
+ * sent to the server. PacketInterceptors are added to the {@link Connection}
+ * together with a {@link org.jivesoftware.smack.filter.PacketFilter} so that only
+ * certain packets are intercepted and processed by the interceptor.<p>
+ *
+ * This allows event-style programming -- every time a new packet is found,
+ * the {@link #interceptPacket(Packet)} method will be called.
+ *
+ * @see Connection#addPacketInterceptor(PacketInterceptor, org.jivesoftware.smack.filter.PacketFilter)
+ * @author Gaston Dombiak
+ */
+public interface PacketInterceptor {
+
+    /**
+     * Process the packet that is about to be sent to the server. The intercepted
+     * packet can be modified by the interceptor.<p>
+     *
+     * Interceptors are invoked using the same thread that requested the packet
+     * to be sent, so it's very important that implementations of this method
+     * not block for any extended period of time.
+     *
+     * @param packet the packet to is going to be sent to the server.
+     */
+    public void interceptPacket(Packet packet);
+}
diff --git a/src/org/jivesoftware/smack/PacketListener.java b/src/org/jivesoftware/smack/PacketListener.java
new file mode 100644
index 0000000..4bc83aa
--- /dev/null
+++ b/src/org/jivesoftware/smack/PacketListener.java
@@ -0,0 +1,48 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Provides a mechanism to listen for packets that pass a specified filter.
+ * This allows event-style programming -- every time a new packet is found,
+ * the {@link #processPacket(Packet)} method will be called. This is the
+ * opposite approach to the functionality provided by a {@link PacketCollector}
+ * which lets you block while waiting for results.
+ *
+ * @see Connection#addPacketListener(PacketListener, org.jivesoftware.smack.filter.PacketFilter)
+ * @author Matt Tucker
+ */
+public interface PacketListener {
+
+    /**
+     * Process the next packet sent to this packet listener.<p>
+     *
+     * A single thread is responsible for invoking all listeners, so
+     * it's very important that implementations of this method not block
+     * for any extended period of time.
+     *
+     * @param packet the packet to process.
+     */
+    public void processPacket(Packet packet);
+
+}
diff --git a/src/org/jivesoftware/smack/PacketReader.java b/src/org/jivesoftware/smack/PacketReader.java
new file mode 100644
index 0000000..05ffc67
--- /dev/null
+++ b/src/org/jivesoftware/smack/PacketReader.java
@@ -0,0 +1,429 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.Connection.ListenerWrapper;
+import org.jivesoftware.smack.packet.*;
+import org.jivesoftware.smack.sasl.SASLMechanism.Challenge;
+import org.jivesoftware.smack.sasl.SASLMechanism.Failure;
+import org.jivesoftware.smack.sasl.SASLMechanism.Success;
+import org.jivesoftware.smack.util.PacketParserUtils;
+
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+import java.util.concurrent.*;
+
+/**
+ * Listens for XML traffic from the XMPP server and parses it into packet objects.
+ * The packet reader also invokes all packet listeners and collectors.<p>
+ *
+ * @see Connection#createPacketCollector
+ * @see Connection#addPacketListener
+ * @author Matt Tucker
+ */
+class PacketReader {
+
+    private Thread readerThread;
+    private ExecutorService listenerExecutor;
+
+    private XMPPConnection connection;
+    private XmlPullParser parser;
+    volatile boolean done;
+
+    private String connectionID = null;
+
+    protected PacketReader(final XMPPConnection connection) {
+        this.connection = connection;
+        this.init();
+    }
+
+    /**
+     * Initializes the reader in order to be used. The reader is initialized during the
+     * first connection and when reconnecting due to an abruptly disconnection.
+     */
+    protected void init() {
+        done = false;
+        connectionID = null;
+
+        readerThread = new Thread() {
+            public void run() {
+                parsePackets(this);
+            }
+        };
+        readerThread.setName("Smack Packet Reader (" + connection.connectionCounterValue + ")");
+        readerThread.setDaemon(true);
+
+        // Create an executor to deliver incoming packets to listeners. We'll use a single
+        // thread with an unbounded queue.
+        listenerExecutor = Executors.newSingleThreadExecutor(new ThreadFactory() {
+
+            public Thread newThread(Runnable runnable) {
+                Thread thread = new Thread(runnable,
+                        "Smack Listener Processor (" + connection.connectionCounterValue + ")");
+                thread.setDaemon(true);
+                return thread;
+            }
+        });
+
+        resetParser();
+    }
+
+    /**
+     * Starts the packet reader thread and returns once a connection to the server
+     * has been established. A connection will be attempted for a maximum of five
+     * seconds. An XMPPException will be thrown if the connection fails.
+     *
+     * @throws XMPPException if the server fails to send an opening stream back
+     *      for more than five seconds.
+     */
+    synchronized public void startup() throws XMPPException {
+        readerThread.start();
+        // Wait for stream tag before returning. We'll wait a couple of seconds before
+        // giving up and throwing an error.
+        try {
+            // A waiting thread may be woken up before the wait time or a notify
+            // (although this is a rare thing). Therefore, we continue waiting
+            // until either a connectionID has been set (and hence a notify was
+            // made) or the total wait time has elapsed.
+            int waitTime = SmackConfiguration.getPacketReplyTimeout();
+            wait(3 * waitTime);
+        }
+        catch (InterruptedException ie) {
+            // Ignore.
+        }
+        if (connectionID == null) {
+            throw new XMPPException("Connection failed. No response from server.");
+        }
+        else {
+            connection.connectionID = connectionID;
+        }
+    }
+
+    /**
+     * Shuts the packet reader down.
+     */
+    public void shutdown() {
+        // Notify connection listeners of the connection closing if done hasn't already been set.
+        if (!done) {
+            for (ConnectionListener listener : connection.getConnectionListeners()) {
+                try {
+                    listener.connectionClosed();
+                }
+                catch (Exception e) {
+                    // Catch and print any exception so we can recover
+                    // from a faulty listener and finish the shutdown process
+                    e.printStackTrace();
+                }
+            }
+        }
+        done = true;
+
+        // Shut down the listener executor.
+        listenerExecutor.shutdown();
+    }
+
+    /**
+     * Cleans up all resources used by the packet reader.
+     */
+    void cleanup() {
+        connection.recvListeners.clear();
+        connection.collectors.clear();
+    }
+
+    /**
+     * Resets the parser using the latest connection's reader. Reseting the parser is necessary
+     * when the plain connection has been secured or when a new opening stream element is going
+     * to be sent by the server.
+     */
+    private void resetParser() {
+        try {
+            parser = XmlPullParserFactory.newInstance().newPullParser();
+            parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+            parser.setInput(connection.reader);
+        }
+        catch (XmlPullParserException xppe) {
+            xppe.printStackTrace();
+        }
+    }
+
+    /**
+     * Parse top-level packets in order to process them further.
+     *
+     * @param thread the thread that is being used by the reader to parse incoming packets.
+     */
+    private void parsePackets(Thread thread) {
+        try {
+            int eventType = parser.getEventType();
+            do {
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("message")) {
+                        processPacket(PacketParserUtils.parseMessage(parser));
+                    }
+                    else if (parser.getName().equals("iq")) {
+                        processPacket(PacketParserUtils.parseIQ(parser, connection));
+                    }
+                    else if (parser.getName().equals("presence")) {
+                        processPacket(PacketParserUtils.parsePresence(parser));
+                    }
+                    // We found an opening stream. Record information about it, then notify
+                    // the connectionID lock so that the packet reader startup can finish.
+                    else if (parser.getName().equals("stream")) {
+                        // Ensure the correct jabber:client namespace is being used.
+                        if ("jabber:client".equals(parser.getNamespace(null))) {
+                            // Get the connection id.
+                            for (int i=0; i<parser.getAttributeCount(); i++) {
+                                if (parser.getAttributeName(i).equals("id")) {
+                                    // Save the connectionID
+                                    connectionID = parser.getAttributeValue(i);
+                                    if (!"1.0".equals(parser.getAttributeValue("", "version"))) {
+                                        // Notify that a stream has been opened if the
+                                        // server is not XMPP 1.0 compliant otherwise make the
+                                        // notification after TLS has been negotiated or if TLS
+                                        // is not supported
+                                        releaseConnectionIDLock();
+                                    }
+                                }
+                                else if (parser.getAttributeName(i).equals("from")) {
+                                    // Use the server name that the server says that it is.
+                                    connection.config.setServiceName(parser.getAttributeValue(i));
+                                }
+                            }
+                        }
+                    }
+                    else if (parser.getName().equals("error")) {
+                        throw new XMPPException(PacketParserUtils.parseStreamError(parser));
+                    }
+                    else if (parser.getName().equals("features")) {
+                        parseFeatures(parser);
+                    }
+                    else if (parser.getName().equals("proceed")) {
+                        // Secure the connection by negotiating TLS
+                        connection.proceedTLSReceived();
+                        // Reset the state of the parser since a new stream element is going
+                        // to be sent by the server
+                        resetParser();
+                    }
+                    else if (parser.getName().equals("failure")) {
+                        String namespace = parser.getNamespace(null);
+                        if ("urn:ietf:params:xml:ns:xmpp-tls".equals(namespace)) {
+                            // TLS negotiation has failed. The server will close the connection
+                            throw new Exception("TLS negotiation has failed");
+                        }
+                        else if ("http://jabber.org/protocol/compress".equals(namespace)) {
+                            // Stream compression has been denied. This is a recoverable
+                            // situation. It is still possible to authenticate and
+                            // use the connection but using an uncompressed connection
+                            connection.streamCompressionDenied();
+                        }
+                        else {
+                            // SASL authentication has failed. The server may close the connection
+                            // depending on the number of retries
+                            final Failure failure = PacketParserUtils.parseSASLFailure(parser);
+                            processPacket(failure);
+                            connection.getSASLAuthentication().authenticationFailed();
+                        }
+                    }
+                    else if (parser.getName().equals("challenge")) {
+                        // The server is challenging the SASL authentication made by the client
+                        String challengeData = parser.nextText();
+                        processPacket(new Challenge(challengeData));
+                        connection.getSASLAuthentication().challengeReceived(challengeData);
+                    }
+                    else if (parser.getName().equals("success")) {
+                        processPacket(new Success(parser.nextText()));
+                        // We now need to bind a resource for the connection
+                        // Open a new stream and wait for the response
+                        connection.packetWriter.openStream();
+                        // Reset the state of the parser since a new stream element is going
+                        // to be sent by the server
+                        resetParser();
+                        // The SASL authentication with the server was successful. The next step
+                        // will be to bind the resource
+                        connection.getSASLAuthentication().authenticated();
+                    }
+                    else if (parser.getName().equals("compressed")) {
+                        // Server confirmed that it's possible to use stream compression. Start
+                        // stream compression
+                        connection.startStreamCompression();
+                        // Reset the state of the parser since a new stream element is going
+                        // to be sent by the server
+                        resetParser();
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("stream")) {
+                        // Disconnect the connection
+                        connection.disconnect();
+                    }
+                }
+                eventType = parser.next();
+            } while (!done && eventType != XmlPullParser.END_DOCUMENT && thread == readerThread);
+        }
+        catch (Exception e) {
+            // The exception can be ignored if the the connection is 'done'
+            // or if the it was caused because the socket got closed
+            if (!(done || connection.isSocketClosed())) {
+                // Close the connection and notify connection listeners of the
+                // error.
+                connection.notifyConnectionError(e);
+            }
+        }
+    }
+
+    /**
+     * Releases the connection ID lock so that the thread that was waiting can resume. The
+     * lock will be released when one of the following three conditions is met:<p>
+     *
+     * 1) An opening stream was sent from a non XMPP 1.0 compliant server
+     * 2) Stream features were received from an XMPP 1.0 compliant server that does not support TLS
+     * 3) TLS negotiation was successful
+     *
+     */
+    synchronized private void releaseConnectionIDLock() {
+        notify();
+    }
+
+    /**
+     * Processes a packet after it's been fully parsed by looping through the installed
+     * packet collectors and listeners and letting them examine the packet to see if
+     * they are a match with the filter.
+     *
+     * @param packet the packet to process.
+     */
+    private void processPacket(Packet packet) {
+        if (packet == null) {
+            return;
+        }
+
+        // Loop through all collectors and notify the appropriate ones.
+        for (PacketCollector collector: connection.getPacketCollectors()) {
+            collector.processPacket(packet);
+        }
+
+        // Deliver the incoming packet to listeners.
+        listenerExecutor.submit(new ListenerNotification(packet));
+    }
+
+    private void parseFeatures(XmlPullParser parser) throws Exception {
+        boolean startTLSReceived = false;
+        boolean startTLSRequired = false;
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("starttls")) {
+                    startTLSReceived = true;
+                }
+                else if (parser.getName().equals("mechanisms")) {
+                    // The server is reporting available SASL mechanisms. Store this information
+                    // which will be used later while logging (i.e. authenticating) into
+                    // the server
+                    connection.getSASLAuthentication()
+                            .setAvailableSASLMethods(PacketParserUtils.parseMechanisms(parser));
+                }
+                else if (parser.getName().equals("bind")) {
+                    // The server requires the client to bind a resource to the stream
+                    connection.getSASLAuthentication().bindingRequired();
+                }
+                else if(parser.getName().equals("ver")){
+                	connection.getConfiguration().setRosterVersioningAvailable(true);
+                }
+                // Set the entity caps node for the server if one is send
+                // See http://xmpp.org/extensions/xep-0115.html#stream
+                else if (parser.getName().equals("c")) {
+                    String node = parser.getAttributeValue(null, "node");
+                    String ver = parser.getAttributeValue(null, "ver");
+                    if (ver != null && node != null) {
+                        String capsNode = node + "#" + ver;
+                        // In order to avoid a dependency from smack to smackx
+                        // we have to set the services caps node in the connection
+                        // and not directly in the EntityCapsManager
+                        connection.setServiceCapsNode(capsNode);
+                    }
+                }
+                else if (parser.getName().equals("session")) {
+                    // The server supports sessions
+                    connection.getSASLAuthentication().sessionsSupported();
+                }
+                else if (parser.getName().equals("compression")) {
+                    // The server supports stream compression
+                    connection.setAvailableCompressionMethods(PacketParserUtils.parseCompressionMethods(parser));
+                }
+                else if (parser.getName().equals("register")) {
+                    connection.getAccountManager().setSupportsAccountCreation(true);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("starttls")) {
+                    // Confirm the server that we want to use TLS
+                    connection.startTLSReceived(startTLSRequired);
+                }
+                else if (parser.getName().equals("required") && startTLSReceived) {
+                    startTLSRequired = true;
+                }
+                else if (parser.getName().equals("features")) {
+                    done = true;
+                }
+            }
+        }
+
+        // If TLS is required but the server doesn't offer it, disconnect
+        // from the server and throw an error. First check if we've already negotiated TLS
+        // and are secure, however (features get parsed a second time after TLS is established).
+        if (!connection.isSecureConnection()) {
+            if (!startTLSReceived && connection.getConfiguration().getSecurityMode() ==
+                    ConnectionConfiguration.SecurityMode.required)
+            {
+                throw new XMPPException("Server does not support security (TLS), " +
+                        "but security required by connection configuration.",
+                        new XMPPError(XMPPError.Condition.forbidden));
+            }
+        }
+        
+        // Release the lock after TLS has been negotiated or we are not insterested in TLS
+        if (!startTLSReceived || connection.getConfiguration().getSecurityMode() ==
+                ConnectionConfiguration.SecurityMode.disabled)
+        {
+            releaseConnectionIDLock();
+        }
+    }
+
+    /**
+     * A runnable to notify all listeners of a packet.
+     */
+    private class ListenerNotification implements Runnable {
+
+        private Packet packet;
+
+        public ListenerNotification(Packet packet) {
+            this.packet = packet;
+        }
+
+        public void run() {
+            for (ListenerWrapper listenerWrapper : connection.recvListeners.values()) {
+                listenerWrapper.notifyListener(packet);
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/PacketWriter.java b/src/org/jivesoftware/smack/PacketWriter.java
new file mode 100644
index 0000000..675af25
--- /dev/null
+++ b/src/org/jivesoftware/smack/PacketWriter.java
@@ -0,0 +1,240 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Packet;
+
+import java.io.IOException;
+import java.io.Writer;
+import java.util.concurrent.ArrayBlockingQueue;
+import java.util.concurrent.BlockingQueue;
+
+/**
+ * Writes packets to a XMPP server. Packets are sent using a dedicated thread. Packet
+ * interceptors can be registered to dynamically modify packets before they're actually
+ * sent. Packet listeners can be registered to listen for all outgoing packets.
+ *
+ * @see Connection#addPacketInterceptor
+ * @see Connection#addPacketSendingListener
+ *
+ * @author Matt Tucker
+ */
+class PacketWriter {
+
+    private Thread writerThread;
+    private Thread keepAliveThread;
+    private Writer writer;
+    private XMPPConnection connection;
+    private final BlockingQueue<Packet> queue;
+    volatile boolean done;
+
+    /**
+     * Creates a new packet writer with the specified connection.
+     *
+     * @param connection the connection.
+     */
+    protected PacketWriter(XMPPConnection connection) {
+        this.queue = new ArrayBlockingQueue<Packet>(500, true);
+        this.connection = connection;
+        init();
+    }
+
+    /** 
+    * Initializes the writer in order to be used. It is called at the first connection and also 
+    * is invoked if the connection is disconnected by an error.
+    */ 
+    protected void init() {
+        this.writer = connection.writer;
+        done = false;
+
+        writerThread = new Thread() {
+            public void run() {
+                writePackets(this);
+            }
+        };
+        writerThread.setName("Smack Packet Writer (" + connection.connectionCounterValue + ")");
+        writerThread.setDaemon(true);
+    }
+    
+    /**
+     * Sends the specified packet to the server.
+     *
+     * @param packet the packet to send.
+     */
+    public void sendPacket(Packet packet) {
+        if (!done) {
+            // Invoke interceptors for the new packet that is about to be sent. Interceptors
+            // may modify the content of the packet.
+            connection.firePacketInterceptors(packet);
+
+            try {
+                queue.put(packet);
+            }
+            catch (InterruptedException ie) {
+                ie.printStackTrace();
+                return;
+            }
+            synchronized (queue) {
+                queue.notifyAll();
+            }
+
+            // Process packet writer listeners. Note that we're using the sending
+            // thread so it's expected that listeners are fast.
+            connection.firePacketSendingListeners(packet);
+        }
+    }
+
+    /**
+     * Starts the packet writer thread and opens a connection to the server. The
+     * packet writer will continue writing packets until {@link #shutdown} or an
+     * error occurs.
+     */
+    public void startup() {
+        writerThread.start();
+    }
+
+    void setWriter(Writer writer) {
+        this.writer = writer;
+    }
+
+    /**
+     * Shuts down the packet writer. Once this method has been called, no further
+     * packets will be written to the server.
+     */
+    public void shutdown() {
+        done = true;
+        synchronized (queue) {
+            queue.notifyAll();
+        }
+        // Interrupt the keep alive thread if one was created
+        if (keepAliveThread != null)
+                keepAliveThread.interrupt();
+    }
+
+    /**
+     * Cleans up all resources used by the packet writer.
+     */
+    void cleanup() {
+        connection.interceptors.clear();
+        connection.sendListeners.clear();
+    }
+
+    /**
+     * Returns the next available packet from the queue for writing.
+     *
+     * @return the next packet for writing.
+     */
+    private Packet nextPacket() {
+        Packet packet = null;
+        // Wait until there's a packet or we're done.
+        while (!done && (packet = queue.poll()) == null) {
+            try {
+                synchronized (queue) {
+                    queue.wait();
+                }
+            }
+            catch (InterruptedException ie) {
+                // Do nothing
+            }
+        }
+        return packet;
+    }
+
+    private void writePackets(Thread thisThread) {
+        try {
+            // Open the stream.
+            openStream();
+            // Write out packets from the queue.
+            while (!done && (writerThread == thisThread)) {
+                Packet packet = nextPacket();
+                if (packet != null) {
+                    writer.write(packet.toXML());
+                    if (queue.isEmpty()) {
+                        writer.flush();
+                    }
+                }
+            }
+            // Flush out the rest of the queue. If the queue is extremely large, it's possible
+            // we won't have time to entirely flush it before the socket is forced closed
+            // by the shutdown process.
+            try {
+                while (!queue.isEmpty()) {
+                    Packet packet = queue.remove();
+                    writer.write(packet.toXML());
+                }
+                writer.flush();
+            }
+            catch (Exception e) {
+                e.printStackTrace();
+            }
+
+            // Delete the queue contents (hopefully nothing is left).
+            queue.clear();
+
+            // Close the stream.
+            try {
+                writer.write("</stream:stream>");
+                writer.flush();
+            }
+            catch (Exception e) {
+                // Do nothing
+            }
+            finally {
+                try {
+                    writer.close();
+                }
+                catch (Exception e) {
+                    // Do nothing
+                }
+            }
+        }
+        catch (IOException ioe) {
+            // The exception can be ignored if the the connection is 'done'
+            // or if the it was caused because the socket got closed
+            if (!(done || connection.isSocketClosed())) {
+                done = true;
+                // packetReader could be set to null by an concurrent disconnect() call.
+                // Therefore Prevent NPE exceptions by checking packetReader.
+                if (connection.packetReader != null) {
+                        connection.notifyConnectionError(ioe);
+                }
+            }
+        }
+    }
+
+    /**
+     * Sends to the server a new stream element. This operation may be requested several times
+     * so we need to encapsulate the logic in one place. This message will be sent while doing
+     * TLS, SASL and resource binding.
+     *
+     * @throws IOException If an error occurs while sending the stanza to the server.
+     */
+    void openStream() throws IOException {
+        StringBuilder stream = new StringBuilder();
+        stream.append("<stream:stream");
+        stream.append(" to=\"").append(connection.getServiceName()).append("\"");
+        stream.append(" xmlns=\"jabber:client\"");
+        stream.append(" xmlns:stream=\"http://etherx.jabber.org/streams\"");
+        stream.append(" version=\"1.0\">");
+        writer.write(stream.toString());
+        writer.flush();
+    }
+}
diff --git a/src/org/jivesoftware/smack/PrivacyList.java b/src/org/jivesoftware/smack/PrivacyList.java
new file mode 100644
index 0000000..67d731d
--- /dev/null
+++ b/src/org/jivesoftware/smack/PrivacyList.java
@@ -0,0 +1,74 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.PrivacyItem;
+
+import java.util.List;
+
+/**
+ * A privacy list represents a list of contacts that is a read only class used to represent a set of allowed or blocked communications. 
+ * Basically it can:<ul>
+ *
+ *      <li>Handle many {@link org.jivesoftware.smack.packet.PrivacyItem}.</li>
+ *      <li>Answer if it is the default list.</li>
+ *      <li>Answer if it is the active list.</li>
+ * </ul>
+ *
+ * {@link PrivacyItem Privacy Items} can handle different kind of blocking communications based on JID, group,
+ * subscription type or globally.
+ * 
+ * @author Francisco Vives
+ */
+public class PrivacyList {
+
+    /** Holds if it is an active list or not **/
+    private boolean isActiveList;
+    /** Holds if it is an default list or not **/
+    private boolean isDefaultList;
+    /** Holds the list name used to print **/
+    private String listName;
+    /** Holds the list of {@see PrivacyItem} **/
+    private List<PrivacyItem> items;
+    
+    protected PrivacyList(boolean isActiveList, boolean isDefaultList,
+            String listName, List<PrivacyItem> privacyItems) {
+        super();
+        this.isActiveList = isActiveList;
+        this.isDefaultList = isDefaultList;
+        this.listName = listName;
+        this.items = privacyItems;
+    }
+
+    public boolean isActiveList() {
+        return isActiveList;
+    }
+
+    public boolean isDefaultList() {
+        return isDefaultList;
+    }
+
+    public List<PrivacyItem> getItems() {
+        return items;
+    }
+
+    public String toString() {
+        return listName;
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/PrivacyListListener.java b/src/org/jivesoftware/smack/PrivacyListListener.java
new file mode 100644
index 0000000..5644ed7
--- /dev/null
+++ b/src/org/jivesoftware/smack/PrivacyListListener.java
@@ -0,0 +1,51 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2006-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.PrivacyItem;
+
+import java.util.List;
+
+/**
+ * Interface to implement classes to listen for server events about privacy communication. 
+ * Listeners are registered with the {@link PrivacyListManager}.
+ *
+ * @see PrivacyListManager#addListener
+ * 
+ * @author Francisco Vives
+ */
+public interface PrivacyListListener {
+
+    /**
+     * Set or update a privacy list with PrivacyItem.
+     *
+     * @param listName the name of the new or updated privacy list.
+     * @param listItem the PrivacyItems that rules the list.
+     */
+    public void setPrivacyList(String listName, List<PrivacyItem> listItem);
+
+    /**
+     * A privacy list has been modified by another. It gets notified.
+     *
+     * @param listName the name of the updated privacy list.
+     */
+    public void updatedPrivacyList(String listName);
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/PrivacyListManager.java b/src/org/jivesoftware/smack/PrivacyListManager.java
new file mode 100644
index 0000000..4dcc9e1
--- /dev/null
+++ b/src/org/jivesoftware/smack/PrivacyListManager.java
@@ -0,0 +1,467 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2006-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.*;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Privacy;
+import org.jivesoftware.smack.packet.PrivacyItem;
+
+import java.util.*;
+
+/**
+ * A PrivacyListManager is used by XMPP clients to block or allow communications from other
+ * users. Use the manager to: <ul>
+ *      <li>Retrieve privacy lists.
+ *      <li>Add, remove, and edit privacy lists.
+ *      <li>Set, change, or decline active lists.
+ *      <li>Set, change, or decline the default list (i.e., the list that is active by default).
+ * </ul>
+ * Privacy Items can handle different kind of permission communications based on JID, group, 
+ * subscription type or globally (@see PrivacyItem).
+ * 
+ * @author Francisco Vives
+ */
+public class PrivacyListManager {
+
+    // Keep the list of instances of this class.
+    private static Map<Connection, PrivacyListManager> instances = Collections
+            .synchronizedMap(new WeakHashMap<Connection, PrivacyListManager>());
+
+	private Connection connection;
+	private final List<PrivacyListListener> listeners = new ArrayList<PrivacyListListener>();
+	PacketFilter packetFilter = new AndFilter(new IQTypeFilter(IQ.Type.SET),
+    		new PacketExtensionFilter("query", "jabber:iq:privacy"));
+
+    static {
+        // Create a new PrivacyListManager on every established connection. In the init()
+        // method of PrivacyListManager, we'll add a listener that will delete the
+        // instance when the connection is closed.
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new PrivacyListManager(connection);
+            }
+        });
+    }
+    /**
+     * Creates a new privacy manager to maintain the communication privacy. Note: no
+     * information is sent to or received from the server until you attempt to 
+     * get or set the privacy communication.<p>
+     *
+     * @param connection the XMPP connection.
+     */
+	private PrivacyListManager(Connection connection) {
+        this.connection = connection;
+        this.init();
+    }
+
+	/** Answer the connection userJID that owns the privacy.
+	 * @return the userJID that owns the privacy
+	 */
+	private String getUser() {
+		return connection.getUser();
+	}
+
+    /**
+     * Initializes the packet listeners of the connection that will notify for any set privacy 
+     * package. 
+     */
+    private void init() {
+        // Register the new instance and associate it with the connection 
+        instances.put(connection, this);
+        // Add a listener to the connection that removes the registered instance when
+        // the connection is closed
+        connection.addConnectionListener(new ConnectionListener() {
+            public void connectionClosed() {
+                // Unregister this instance since the connection has been closed
+                instances.remove(connection);
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                // ignore
+            }
+
+            public void reconnectionFailed(Exception e) {
+                // ignore
+            }
+
+            public void reconnectingIn(int seconds) {
+                // ignore
+            }
+
+            public void reconnectionSuccessful() {
+                // ignore
+            }
+        });
+
+        connection.addPacketListener(new PacketListener() {
+            public void processPacket(Packet packet) {
+
+                if (packet == null || packet.getError() != null) {
+                    return;
+                }
+                // The packet is correct.
+                Privacy privacy = (Privacy) packet;
+                
+                // Notifies the event to the listeners.
+                synchronized (listeners) {
+                    for (PrivacyListListener listener : listeners) {
+                        // Notifies the created or updated privacy lists
+                        for (Map.Entry<String,List<PrivacyItem>> entry : privacy.getItemLists().entrySet()) {
+                            String listName = entry.getKey();
+                            List<PrivacyItem> items = entry.getValue();
+                            if (items.isEmpty()) {
+                                listener.updatedPrivacyList(listName);
+                            } else {
+                                listener.setPrivacyList(listName, items);
+                            }
+                        }
+                    }
+                }
+                
+                // Send a result package acknowledging the reception of a privacy package.
+                
+                // Prepare the IQ packet to send
+                IQ iq = new IQ() {
+                    public String getChildElementXML() {
+                        return "";
+                    }
+                };
+                iq.setType(IQ.Type.RESULT);
+                iq.setFrom(packet.getFrom());
+                iq.setPacketID(packet.getPacketID());
+
+                // Send create & join packet.
+                connection.sendPacket(iq);
+            }
+        }, packetFilter);
+    }
+
+    /**
+     * Returns the PrivacyListManager instance associated with a given Connection.
+     * 
+     * @param connection the connection used to look for the proper PrivacyListManager.
+     * @return the PrivacyListManager associated with a given Connection.
+     */
+    public static PrivacyListManager getInstanceFor(Connection connection) {
+        return instances.get(connection);
+    }
+    
+	/**
+	 * Send the {@link Privacy} packet to the server in order to know some privacy content and then 
+	 * waits for the answer.
+	 * 
+	 * @param requestPrivacy is the {@link Privacy} packet configured properly whose XML
+     *      will be sent to the server.
+	 * @return a new {@link Privacy} with the data received from the server.
+	 * @exception XMPPException if the request or the answer failed, it raises an exception.
+	 */ 
+	private Privacy getRequest(Privacy requestPrivacy) throws XMPPException {
+		// The request is a get iq type
+		requestPrivacy.setType(Privacy.Type.GET);
+		requestPrivacy.setFrom(this.getUser());
+		
+		// Filter packets looking for an answer from the server.
+		PacketFilter responseFilter = new PacketIDFilter(requestPrivacy.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        
+        // Send create & join packet.
+        connection.sendPacket(requestPrivacy);
+        
+        // Wait up to a certain number of seconds for a reply.
+        Privacy privacyAnswer =
+            (Privacy) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        
+        // Stop queuing results
+        response.cancel();
+
+        // Interprete the result and answer the privacy only if it is valid
+        if (privacyAnswer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (privacyAnswer.getError() != null) {
+            throw new XMPPException(privacyAnswer.getError());
+        }
+        return privacyAnswer;
+	}
+	
+	/**
+	 * Send the {@link Privacy} packet to the server in order to modify the server privacy and 
+	 * waits for the answer.
+	 * 
+	 * @param requestPrivacy is the {@link Privacy} packet configured properly whose xml will be sent
+	 * to the server.
+	 * @return a new {@link Privacy} with the data received from the server.
+	 * @exception XMPPException if the request or the answer failed, it raises an exception.
+	 */ 
+	private Packet setRequest(Privacy requestPrivacy) throws XMPPException {
+		
+		// The request is a get iq type
+		requestPrivacy.setType(Privacy.Type.SET);
+		requestPrivacy.setFrom(this.getUser());
+		
+		// Filter packets looking for an answer from the server.
+		PacketFilter responseFilter = new PacketIDFilter(requestPrivacy.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        
+        // Send create & join packet.
+        connection.sendPacket(requestPrivacy);
+        
+        // Wait up to a certain number of seconds for a reply.
+        Packet privacyAnswer = response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        
+        // Stop queuing results
+        response.cancel();
+
+        // Interprete the result and answer the privacy only if it is valid
+        if (privacyAnswer == null) {
+            throw new XMPPException("No response from server.");
+        } else if (privacyAnswer.getError() != null) {
+            throw new XMPPException(privacyAnswer.getError());
+        }
+        return privacyAnswer;
+	}
+
+	/**
+	 * Answer a privacy containing the list structre without {@link PrivacyItem}.
+	 * 
+	 * @return a Privacy with the list names.
+     * @throws XMPPException if an error occurs.
+	 */ 
+	private Privacy getPrivacyWithListNames() throws XMPPException {
+		
+		// The request of the list is an empty privacy message
+		Privacy request = new Privacy();
+		
+		// Send the package to the server and get the answer
+		return getRequest(request);
+	}
+	
+    /**
+     * Answer the active privacy list.
+     * 
+     * @return the privacy list of the active list.
+     * @throws XMPPException if an error occurs.
+     */ 
+    public PrivacyList getActiveList() throws XMPPException {
+        Privacy privacyAnswer = this.getPrivacyWithListNames();
+        String listName = privacyAnswer.getActiveName();
+        boolean isDefaultAndActive = privacyAnswer.getActiveName() != null
+                && privacyAnswer.getDefaultName() != null
+                && privacyAnswer.getActiveName().equals(
+                privacyAnswer.getDefaultName());
+        return new PrivacyList(true, isDefaultAndActive, listName, getPrivacyListItems(listName));
+    }
+    
+    /**
+     * Answer the default privacy list.
+     * 
+     * @return the privacy list of the default list.
+     * @throws XMPPException if an error occurs.
+     */ 
+    public PrivacyList getDefaultList() throws XMPPException {
+        Privacy privacyAnswer = this.getPrivacyWithListNames();
+        String listName = privacyAnswer.getDefaultName();
+        boolean isDefaultAndActive = privacyAnswer.getActiveName() != null
+                && privacyAnswer.getDefaultName() != null
+                && privacyAnswer.getActiveName().equals(
+                privacyAnswer.getDefaultName());
+        return new PrivacyList(isDefaultAndActive, true, listName, getPrivacyListItems(listName));
+    }
+    
+    /**
+     * Answer the privacy list items under listName with the allowed and blocked permissions.
+     * 
+     * @param listName the name of the list to get the allowed and blocked permissions.
+     * @return a list of privacy items under the list listName.
+     * @throws XMPPException if an error occurs.
+     */ 
+    private List<PrivacyItem> getPrivacyListItems(String listName) throws XMPPException {
+        
+        // The request of the list is an privacy message with an empty list
+        Privacy request = new Privacy();
+        request.setPrivacyList(listName, new ArrayList<PrivacyItem>());
+        
+        // Send the package to the server and get the answer
+        Privacy privacyAnswer = getRequest(request);
+        
+        return privacyAnswer.getPrivacyList(listName);
+    }
+    
+	/**
+	 * Answer the privacy list items under listName with the allowed and blocked permissions.
+	 * 
+	 * @param listName the name of the list to get the allowed and blocked permissions.
+	 * @return a privacy list under the list listName.
+     * @throws XMPPException if an error occurs.
+	 */ 
+	public PrivacyList getPrivacyList(String listName) throws XMPPException {
+		
+        return new PrivacyList(false, false, listName, getPrivacyListItems(listName));
+	}
+	
+    /**
+     * Answer every privacy list with the allowed and blocked permissions.
+     * 
+     * @return an array of privacy lists.
+     * @throws XMPPException if an error occurs.
+     */ 
+    public PrivacyList[] getPrivacyLists() throws XMPPException {
+        Privacy privacyAnswer = this.getPrivacyWithListNames();
+        Set<String> names = privacyAnswer.getPrivacyListNames();
+        PrivacyList[] lists = new PrivacyList[names.size()];
+        boolean isActiveList;
+        boolean isDefaultList;
+        int index=0;
+        for (String listName : names) {
+            isActiveList = listName.equals(privacyAnswer.getActiveName());
+            isDefaultList = listName.equals(privacyAnswer.getDefaultName());
+            lists[index] = new PrivacyList(isActiveList, isDefaultList,
+                    listName, getPrivacyListItems(listName));
+            index = index + 1;
+        }
+        return lists;
+    }
+
+    
+	/**
+	 * Set or change the active list to listName.
+	 * 
+	 * @param listName the list name to set as the active one.
+	 * @exception XMPPException if the request or the answer failed, it raises an exception.
+	 */ 
+	public void setActiveListName(String listName) throws XMPPException {
+		
+		// The request of the list is an privacy message with an empty list
+		Privacy request = new Privacy();
+		request.setActiveName(listName);
+		
+		// Send the package to the server
+		setRequest(request);
+	}
+
+	/**
+	 * Client declines the use of active lists.
+     *
+     * @throws XMPPException if an error occurs.
+	 */ 
+	public void declineActiveList() throws XMPPException {
+		
+		// The request of the list is an privacy message with an empty list
+		Privacy request = new Privacy();
+		request.setDeclineActiveList(true);
+		
+		// Send the package to the server
+		setRequest(request);
+	}
+
+	/**
+	 * Set or change the default list to listName.
+	 * 
+	 * @param listName the list name to set as the default one.
+	 * @exception XMPPException if the request or the answer failed, it raises an exception.
+	 */ 
+	public void setDefaultListName(String listName) throws XMPPException {
+		
+		// The request of the list is an privacy message with an empty list
+		Privacy request = new Privacy();
+		request.setDefaultName(listName);
+		
+		// Send the package to the server
+		setRequest(request);
+	}
+	
+	/**
+	 * Client declines the use of default lists.
+     *
+     * @throws XMPPException if an error occurs.
+	 */ 
+	public void declineDefaultList() throws XMPPException {
+		
+		// The request of the list is an privacy message with an empty list
+		Privacy request = new Privacy();
+		request.setDeclineDefaultList(true);
+		
+		// Send the package to the server
+		setRequest(request);
+	}
+	
+	/**
+	 * The client has created a new list. It send the new one to the server.
+	 * 
+     * @param listName the list that has changed its content.
+     * @param privacyItems a List with every privacy item in the list.
+     * @throws XMPPException if an error occurs.
+	 */ 
+	public void createPrivacyList(String listName, List<PrivacyItem> privacyItems) throws XMPPException {
+
+		this.updatePrivacyList(listName, privacyItems);
+	}
+
+    /**
+     * The client has edited an existing list. It updates the server content with the resulting 
+     * list of privacy items. The {@link PrivacyItem} list MUST contain all elements in the 
+     * list (not the "delta").
+     * 
+     * @param listName the list that has changed its content.
+     * @param privacyItems a List with every privacy item in the list.
+     * @throws XMPPException if an error occurs.
+     */ 
+    public void updatePrivacyList(String listName, List<PrivacyItem> privacyItems) throws XMPPException {
+
+        // Build the privacy package to add or update the new list
+        Privacy request = new Privacy();
+        request.setPrivacyList(listName, privacyItems);
+
+        // Send the package to the server
+        setRequest(request);
+    }
+    
+	/**
+	 * Remove a privacy list.
+	 * 
+     * @param listName the list that has changed its content.
+     * @throws XMPPException if an error occurs.
+	 */ 
+	public void deletePrivacyList(String listName) throws XMPPException {
+		
+		// The request of the list is an privacy message with an empty list
+		Privacy request = new Privacy();
+		request.setPrivacyList(listName, new ArrayList<PrivacyItem>());
+
+		// Send the package to the server
+		setRequest(request);
+	}
+	
+    /**
+     * Adds a packet listener that will be notified of any new update in the user
+     * privacy communication.
+     *
+     * @param listener a packet listener.
+     */
+    public void addListener(PrivacyListListener listener) {
+        // Keep track of the listener so that we can manually deliver extra
+        // messages to it later if needed.
+        synchronized (listeners) {
+            listeners.add(listener);
+        }
+    }    
+}
diff --git a/src/org/jivesoftware/smack/ReconnectionManager.java b/src/org/jivesoftware/smack/ReconnectionManager.java
new file mode 100644
index 0000000..cc3e3af
--- /dev/null
+++ b/src/org/jivesoftware/smack/ReconnectionManager.java
@@ -0,0 +1,227 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.StreamError;
+import java.util.Random;
+/**
+ * Handles the automatic reconnection process. Every time a connection is dropped without
+ * the application explictly closing it, the manager automatically tries to reconnect to
+ * the server.<p>
+ *
+ * The reconnection mechanism will try to reconnect periodically:
+ * <ol>
+ *  <li>For the first minute it will attempt to connect once every ten seconds.
+ *  <li>For the next five minutes it will attempt to connect once a minute.
+ *  <li>If that fails it will indefinitely try to connect once every five minutes.
+ * </ol>
+ *
+ * @author Francisco Vives
+ */
+public class ReconnectionManager implements ConnectionListener {
+
+    // Holds the connection to the server
+    private Connection connection;
+    private Thread reconnectionThread;
+    private int randomBase = new Random().nextInt(11) + 5; // between 5 and 15 seconds
+    
+    // Holds the state of the reconnection
+    boolean done = false;
+
+    static {
+        // Create a new PrivacyListManager on every established connection. In the init()
+        // method of PrivacyListManager, we'll add a listener that will delete the
+        // instance when the connection is closed.
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                connection.addConnectionListener(new ReconnectionManager(connection));
+            }
+        });
+    }
+
+    private ReconnectionManager(Connection connection) {
+        this.connection = connection;
+    }
+
+
+    /**
+     * Returns true if the reconnection mechanism is enabled.
+     *
+     * @return true if automatic reconnections are allowed.
+     */
+    private boolean isReconnectionAllowed() {
+        return !done && !connection.isConnected()
+                && connection.isReconnectionAllowed();
+    }
+
+    /**
+     * Starts a reconnection mechanism if it was configured to do that.
+     * The algorithm is been executed when the first connection error is detected.
+     * <p/>
+     * The reconnection mechanism will try to reconnect periodically in this way:
+     * <ol>
+     * <li>First it will try 6 times every 10 seconds.
+     * <li>Then it will try 10 times every 1 minute.
+     * <li>Finally it will try indefinitely every 5 minutes.
+     * </ol>
+     */
+    synchronized protected void reconnect() {
+        if (this.isReconnectionAllowed()) {
+            // Since there is no thread running, creates a new one to attempt
+            // the reconnection.
+            // avoid to run duplicated reconnectionThread -- fd: 16/09/2010
+            if (reconnectionThread!=null && reconnectionThread.isAlive()) return;
+            
+            reconnectionThread = new Thread() {
+             			
+                /**
+                 * Holds the current number of reconnection attempts
+                 */
+                private int attempts = 0;
+
+                /**
+                 * Returns the number of seconds until the next reconnection attempt.
+                 *
+                 * @return the number of seconds until the next reconnection attempt.
+                 */
+                private int timeDelay() {
+                    attempts++;
+                    if (attempts > 13) {
+                	return randomBase*6*5;      // between 2.5 and 7.5 minutes (~5 minutes)
+                    }
+                    if (attempts > 7) {
+                	return randomBase*6;       // between 30 and 90 seconds (~1 minutes)
+                    }
+                    return randomBase;       // 10 seconds
+                }
+
+                /**
+                 * The process will try the reconnection until the connection succeed or the user
+                 * cancell it
+                 */
+                public void run() {
+                    // The process will try to reconnect until the connection is established or
+                    // the user cancel the reconnection process {@link Connection#disconnect()}
+                    while (ReconnectionManager.this.isReconnectionAllowed()) {
+                        // Find how much time we should wait until the next reconnection
+                        int remainingSeconds = timeDelay();
+                        // Sleep until we're ready for the next reconnection attempt. Notify
+                        // listeners once per second about how much time remains before the next
+                        // reconnection attempt.
+                        while (ReconnectionManager.this.isReconnectionAllowed() &&
+                                remainingSeconds > 0)
+                        {
+                            try {
+                                Thread.sleep(1000);
+                                remainingSeconds--;
+                                ReconnectionManager.this
+                                        .notifyAttemptToReconnectIn(remainingSeconds);
+                            }
+                            catch (InterruptedException e1) {
+                                e1.printStackTrace();
+                                // Notify the reconnection has failed
+                                ReconnectionManager.this.notifyReconnectionFailed(e1);
+                            }
+                        }
+
+                        // Makes a reconnection attempt
+                        try {
+                            if (ReconnectionManager.this.isReconnectionAllowed()) {
+                                connection.connect();
+                            }
+                        }
+                        catch (XMPPException e) {
+                            // Fires the failed reconnection notification
+                            ReconnectionManager.this.notifyReconnectionFailed(e);
+                        }
+                    }
+                }
+            };
+            reconnectionThread.setName("Smack Reconnection Manager");
+            reconnectionThread.setDaemon(true);
+            reconnectionThread.start();
+        }
+    }
+
+    /**
+     * Fires listeners when a reconnection attempt has failed.
+     *
+     * @param exception the exception that occured.
+     */
+    protected void notifyReconnectionFailed(Exception exception) {
+        if (isReconnectionAllowed()) {
+            for (ConnectionListener listener : connection.connectionListeners) {
+                listener.reconnectionFailed(exception);
+            }
+        }
+    }
+
+    /**
+     * Fires listeners when The Connection will retry a reconnection. Expressed in seconds.
+     *
+     * @param seconds the number of seconds that a reconnection will be attempted in.
+     */
+    protected void notifyAttemptToReconnectIn(int seconds) {
+        if (isReconnectionAllowed()) {
+            for (ConnectionListener listener : connection.connectionListeners) {
+                listener.reconnectingIn(seconds);
+            }
+        }
+    }
+
+    public void connectionClosed() {
+        done = true;
+    }
+
+    public void connectionClosedOnError(Exception e) {
+        done = false;
+        if (e instanceof XMPPException) {
+            XMPPException xmppEx = (XMPPException) e;
+            StreamError error = xmppEx.getStreamError();
+
+            // Make sure the error is not null
+            if (error != null) {
+                String reason = error.getCode();
+
+                if ("conflict".equals(reason)) {
+                    return;
+                }
+            }
+        }
+
+        if (this.isReconnectionAllowed()) {
+            this.reconnect();
+        }
+    }
+
+    public void reconnectingIn(int seconds) {
+        // ignore
+    }
+
+    public void reconnectionFailed(Exception e) {
+        // ignore
+    }
+
+    /**
+     * The connection has successfull gotten connected.
+     */
+    public void reconnectionSuccessful() {
+        // ignore
+    }
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/Roster.java b/src/org/jivesoftware/smack/Roster.java
new file mode 100644
index 0000000..66a78b2
--- /dev/null
+++ b/src/org/jivesoftware/smack/Roster.java
@@ -0,0 +1,1038 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.RosterPacket;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.*;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+/**
+ * Represents a user's roster, which is the collection of users a person receives
+ * presence updates for. Roster items are categorized into groups for easier management.<p>
+ * <p/>
+ * Others users may attempt to subscribe to this user using a subscription request. Three
+ * modes are supported for handling these requests: <ul>
+ * <li>{@link SubscriptionMode#accept_all accept_all} -- accept all subscription requests.</li>
+ * <li>{@link SubscriptionMode#reject_all reject_all} -- reject all subscription requests.</li>
+ * <li>{@link SubscriptionMode#manual manual} -- manually process all subscription requests.</li>
+ * </ul>
+ *
+ * @author Matt Tucker
+ * @see Connection#getRoster()
+ */
+public class Roster {
+
+    /**
+     * The default subscription processing mode to use when a Roster is created. By default
+     * all subscription requests are automatically accepted.
+     */
+    private static SubscriptionMode defaultSubscriptionMode = SubscriptionMode.accept_all;
+    private RosterStorage persistentStorage;
+
+    private Connection connection;
+    private final Map<String, RosterGroup> groups;
+    private final Map<String,RosterEntry> entries;
+    private final List<RosterEntry> unfiledEntries;
+    private final List<RosterListener> rosterListeners;
+    private Map<String, Map<String, Presence>> presenceMap;
+    // The roster is marked as initialized when at least a single roster packet
+    // has been received and processed.
+    boolean rosterInitialized = false;
+    private PresencePacketListener presencePacketListener;
+
+    private SubscriptionMode subscriptionMode = getDefaultSubscriptionMode();
+    
+    private String requestPacketId;
+
+    /**
+     * Returns the default subscription processing mode to use when a new Roster is created. The
+     * subscription processing mode dictates what action Smack will take when subscription
+     * requests from other users are made. The default subscription mode
+     * is {@link SubscriptionMode#accept_all}.
+     *
+     * @return the default subscription mode to use for new Rosters
+     */
+    public static SubscriptionMode getDefaultSubscriptionMode() {
+        return defaultSubscriptionMode;
+    }
+
+    /**
+     * Sets the default subscription processing mode to use when a new Roster is created. The
+     * subscription processing mode dictates what action Smack will take when subscription
+     * requests from other users are made. The default subscription mode
+     * is {@link SubscriptionMode#accept_all}.
+     *
+     * @param subscriptionMode the default subscription mode to use for new Rosters.
+     */
+    public static void setDefaultSubscriptionMode(SubscriptionMode subscriptionMode) {
+        defaultSubscriptionMode = subscriptionMode;
+    }
+    
+    Roster(final Connection connection, RosterStorage persistentStorage){
+    	this(connection);
+    	this.persistentStorage = persistentStorage;
+    }
+
+    /**
+     * Creates a new roster.
+     *
+     * @param connection an XMPP connection.
+     */
+    Roster(final Connection connection) {
+        this.connection = connection;
+        //Disable roster versioning if server doesn't offer support for it
+        if(!connection.getConfiguration().isRosterVersioningAvailable()){
+        	persistentStorage=null;
+        }
+        groups = new ConcurrentHashMap<String, RosterGroup>();
+        unfiledEntries = new CopyOnWriteArrayList<RosterEntry>();
+        entries = new ConcurrentHashMap<String,RosterEntry>();
+        rosterListeners = new CopyOnWriteArrayList<RosterListener>();
+        presenceMap = new ConcurrentHashMap<String, Map<String, Presence>>();
+        // Listen for any roster packets.
+        PacketFilter rosterFilter = new PacketTypeFilter(RosterPacket.class);
+        connection.addPacketListener(new RosterPacketListener(), rosterFilter);
+        // Listen for any presence packets.
+        PacketFilter presenceFilter = new PacketTypeFilter(Presence.class);
+        presencePacketListener = new PresencePacketListener();
+        connection.addPacketListener(presencePacketListener, presenceFilter);
+        
+        // Listen for connection events
+        final ConnectionListener connectionListener = new AbstractConnectionListener() {
+            
+            public void connectionClosed() {
+                // Changes the presence available contacts to unavailable
+                setOfflinePresences();
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                // Changes the presence available contacts to unavailable
+                setOfflinePresences();
+            }
+
+        };
+        
+        // if not connected add listener after successful login
+        if(!this.connection.isConnected()) {
+            Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+                
+                public void connectionCreated(Connection connection) {
+                    if(connection.equals(Roster.this.connection)) {
+                        Roster.this.connection.addConnectionListener(connectionListener);
+                    }
+                    
+                }
+            });
+        } else {
+            connection.addConnectionListener(connectionListener);
+        }
+    }
+
+    /**
+     * Returns the subscription processing mode, which dictates what action
+     * Smack will take when subscription requests from other users are made.
+     * The default subscription mode is {@link SubscriptionMode#accept_all}.<p>
+     * <p/>
+     * If using the manual mode, a PacketListener should be registered that
+     * listens for Presence packets that have a type of
+     * {@link org.jivesoftware.smack.packet.Presence.Type#subscribe}.
+     *
+     * @return the subscription mode.
+     */
+    public SubscriptionMode getSubscriptionMode() {
+        return subscriptionMode;
+    }
+
+    /**
+     * Sets the subscription processing mode, which dictates what action
+     * Smack will take when subscription requests from other users are made.
+     * The default subscription mode is {@link SubscriptionMode#accept_all}.<p>
+     * <p/>
+     * If using the manual mode, a PacketListener should be registered that
+     * listens for Presence packets that have a type of
+     * {@link org.jivesoftware.smack.packet.Presence.Type#subscribe}.
+     *
+     * @param subscriptionMode the subscription mode.
+     */
+    public void setSubscriptionMode(SubscriptionMode subscriptionMode) {
+        this.subscriptionMode = subscriptionMode;
+    }
+
+    /**
+     * Reloads the entire roster from the server. This is an asynchronous operation,
+     * which means the method will return immediately, and the roster will be
+     * reloaded at a later point when the server responds to the reload request.
+     * 
+     * @throws IllegalStateException if connection is not logged in or logged in anonymously
+     */
+    public void reload() {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Not logged in to server.");
+        }
+        if (connection.isAnonymous()) {
+            throw new IllegalStateException("Anonymous users can't have a roster.");
+        }
+
+    	RosterPacket packet = new RosterPacket();
+    	if(persistentStorage!=null){
+    		packet.setVersion(persistentStorage.getRosterVersion());
+    	}
+    	requestPacketId = packet.getPacketID();
+    	PacketFilter idFilter = new PacketIDFilter(requestPacketId);
+    	connection.addPacketListener(new RosterResultListener(), idFilter);
+        connection.sendPacket(packet);
+    }
+
+    /**
+     * Adds a listener to this roster. The listener will be fired anytime one or more
+     * changes to the roster are pushed from the server.
+     *
+     * @param rosterListener a roster listener.
+     */
+    public void addRosterListener(RosterListener rosterListener) {
+        if (!rosterListeners.contains(rosterListener)) {
+            rosterListeners.add(rosterListener);
+        }
+    }
+
+    /**
+     * Removes a listener from this roster. The listener will be fired anytime one or more
+     * changes to the roster are pushed from the server.
+     *
+     * @param rosterListener a roster listener.
+     */
+    public void removeRosterListener(RosterListener rosterListener) {
+        rosterListeners.remove(rosterListener);
+    }
+
+    /**
+     * Creates a new group.<p>
+     * <p/>
+     * Note: you must add at least one entry to the group for the group to be kept
+     * after a logout/login. This is due to the way that XMPP stores group information.
+     *
+     * @param name the name of the group.
+     * @return a new group.
+     * @throws IllegalStateException if connection is not logged in or logged in anonymously
+     */
+    public RosterGroup createGroup(String name) {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Not logged in to server.");
+        }
+        if (connection.isAnonymous()) {
+            throw new IllegalStateException("Anonymous users can't have a roster.");
+        }
+        if (groups.containsKey(name)) {
+            throw new IllegalArgumentException("Group with name " + name + " alread exists.");
+        }
+        
+        RosterGroup group = new RosterGroup(name, connection);
+        groups.put(name, group);
+        return group;
+    }
+
+    /**
+     * Creates a new roster entry and presence subscription. The server will asynchronously
+     * update the roster with the subscription status.
+     *
+     * @param user   the user. (e.g. johndoe@jabber.org)
+     * @param name   the nickname of the user.
+     * @param groups the list of group names the entry will belong to, or <tt>null</tt> if the
+     *               the roster entry won't belong to a group.
+     * @throws XMPPException if an XMPP exception occurs.
+     * @throws IllegalStateException if connection is not logged in or logged in anonymously
+     */
+    public void createEntry(String user, String name, String[] groups) throws XMPPException {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Not logged in to server.");
+        }
+        if (connection.isAnonymous()) {
+            throw new IllegalStateException("Anonymous users can't have a roster.");
+        }
+
+        // Create and send roster entry creation packet.
+        RosterPacket rosterPacket = new RosterPacket();
+        rosterPacket.setType(IQ.Type.SET);
+        RosterPacket.Item item = new RosterPacket.Item(user, name);
+        if (groups != null) {
+            for (String group : groups) {
+                if (group != null && group.trim().length() > 0) {
+                    item.addGroupName(group);
+                }
+            }
+        }
+        rosterPacket.addRosterItem(item);
+        // Wait up to a certain number of seconds for a reply from the server.
+        PacketCollector collector = connection.createPacketCollector(
+                new PacketIDFilter(rosterPacket.getPacketID()));
+        connection.sendPacket(rosterPacket);
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+
+        // Create a presence subscription packet and send.
+        Presence presencePacket = new Presence(Presence.Type.subscribe);
+        presencePacket.setTo(user);
+        connection.sendPacket(presencePacket);
+    }
+    
+    private void insertRosterItems(List<RosterPacket.Item> items){
+    	 Collection<String> addedEntries = new ArrayList<String>();
+         Collection<String> updatedEntries = new ArrayList<String>();
+         Collection<String> deletedEntries = new ArrayList<String>();
+         Iterator<RosterPacket.Item> iter = items.iterator();
+         while(iter.hasNext()){
+        	 insertRosterItem(iter.next(), addedEntries,updatedEntries,deletedEntries);
+         }
+         fireRosterChangedEvent(addedEntries, updatedEntries, deletedEntries);
+    }
+    
+    private void insertRosterItem(RosterPacket.Item item, Collection<String> addedEntries,
+    		Collection<String> updatedEntries, Collection<String> deletedEntries){
+    	RosterEntry entry = new RosterEntry(item.getUser(), item.getName(),
+                item.getItemType(), item.getItemStatus(), this, connection);
+
+        // If the packet is of the type REMOVE then remove the entry
+        if (RosterPacket.ItemType.remove.equals(item.getItemType())) {
+            // Remove the entry from the entry list.
+            if (entries.containsKey(item.getUser())) {
+                entries.remove(item.getUser());
+            }
+            // Remove the entry from the unfiled entry list.
+            if (unfiledEntries.contains(entry)) {
+                unfiledEntries.remove(entry);
+            }
+            // Removing the user from the roster, so remove any presence information
+            // about them.
+            String key = StringUtils.parseName(item.getUser()) + "@" +
+                    StringUtils.parseServer(item.getUser());
+            presenceMap.remove(key);
+            // Keep note that an entry has been removed
+            if(deletedEntries!=null){
+            	deletedEntries.add(item.getUser());
+            }
+        }
+        else {
+            // Make sure the entry is in the entry list.
+            if (!entries.containsKey(item.getUser())) {
+                entries.put(item.getUser(), entry);
+                // Keep note that an entry has been added
+                if(addedEntries!=null){
+                	addedEntries.add(item.getUser());
+                }
+            }
+            else {
+                // If the entry was in then list then update its state with the new values
+                entries.put(item.getUser(), entry);
+                
+                // Keep note that an entry has been updated
+                if(updatedEntries!=null){
+                	updatedEntries.add(item.getUser());
+                }
+            }
+            // If the roster entry belongs to any groups, remove it from the
+            // list of unfiled entries.
+            if (!item.getGroupNames().isEmpty()) {
+                unfiledEntries.remove(entry);
+            }
+            // Otherwise add it to the list of unfiled entries.
+            else {
+                if (!unfiledEntries.contains(entry)) {
+                    unfiledEntries.add(entry);
+                }
+            }
+        }
+
+        // Find the list of groups that the user currently belongs to.
+        List<String> currentGroupNames = new ArrayList<String>();
+        for (RosterGroup group: getGroups()) {
+            if (group.contains(entry)) {
+                currentGroupNames.add(group.getName());
+            }
+        }
+
+        // If the packet is not of the type REMOVE then add the entry to the groups
+        if (!RosterPacket.ItemType.remove.equals(item.getItemType())) {
+            // Create the new list of groups the user belongs to.
+            List<String> newGroupNames = new ArrayList<String>();
+            for (String groupName : item.getGroupNames()) {
+                // Add the group name to the list.
+                newGroupNames.add(groupName);
+
+                // Add the entry to the group.
+                RosterGroup group = getGroup(groupName);
+                if (group == null) {
+                    group = createGroup(groupName);
+                    groups.put(groupName, group);
+                }
+                // Add the entry.
+                group.addEntryLocal(entry);
+            }
+
+            // We have the list of old and new group names. We now need to
+            // remove the entry from the all the groups it may no longer belong
+            // to. We do this by subracting the new group set from the old.
+            for (String newGroupName : newGroupNames) {
+                currentGroupNames.remove(newGroupName);
+            }
+        }
+
+        // Loop through any groups that remain and remove the entries.
+        // This is neccessary for the case of remote entry removals.
+        for (String groupName : currentGroupNames) {
+            RosterGroup group = getGroup(groupName);
+            group.removeEntryLocal(entry);
+            if (group.getEntryCount() == 0) {
+                groups.remove(groupName);
+            }
+        }
+        // Remove all the groups with no entries. We have to do this because
+        // RosterGroup.removeEntry removes the entry immediately (locally) and the
+        // group could remain empty.
+        // TODO Check the performance/logic for rosters with large number of groups
+        for (RosterGroup group : getGroups()) {
+            if (group.getEntryCount() == 0) {
+                groups.remove(group.getName());
+            }
+        }
+    }
+
+    /**
+     * Removes a roster entry from the roster. The roster entry will also be removed from the
+     * unfiled entries or from any roster group where it could belong and will no longer be part
+     * of the roster. Note that this is an asynchronous call -- Smack must wait for the server
+     * to send an updated subscription status.
+     *
+     * @param entry a roster entry.
+     * @throws XMPPException if an XMPP error occurs.
+     * @throws IllegalStateException if connection is not logged in or logged in anonymously
+     */
+    public void removeEntry(RosterEntry entry) throws XMPPException {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Not logged in to server.");
+        }
+        if (connection.isAnonymous()) {
+            throw new IllegalStateException("Anonymous users can't have a roster.");
+        }
+
+        // Only remove the entry if it's in the entry list.
+        // The actual removal logic takes place in RosterPacketListenerprocess>>Packet(Packet)
+        if (!entries.containsKey(entry.getUser())) {
+            return;
+        }
+        RosterPacket packet = new RosterPacket();
+        packet.setType(IQ.Type.SET);
+        RosterPacket.Item item = RosterEntry.toRosterItem(entry);
+        // Set the item type as REMOVE so that the server will delete the entry
+        item.setItemType(RosterPacket.ItemType.remove);
+        packet.addRosterItem(item);
+        PacketCollector collector = connection.createPacketCollector(
+                new PacketIDFilter(packet.getPacketID()));
+        connection.sendPacket(packet);
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Returns a count of the entries in the roster.
+     *
+     * @return the number of entries in the roster.
+     */
+    public int getEntryCount() {
+        return getEntries().size();
+    }
+
+    /**
+     * Returns an unmodifiable collection of all entries in the roster, including entries
+     * that don't belong to any groups.
+     *
+     * @return all entries in the roster.
+     */
+    public Collection<RosterEntry> getEntries() {
+        Set<RosterEntry> allEntries = new HashSet<RosterEntry>();
+        // Loop through all roster groups and add their entries to the answer
+        for (RosterGroup rosterGroup : getGroups()) {
+            allEntries.addAll(rosterGroup.getEntries());
+        }
+        // Add the roster unfiled entries to the answer
+        allEntries.addAll(unfiledEntries);
+
+        return Collections.unmodifiableCollection(allEntries);
+    }
+
+    /**
+     * Returns a count of the unfiled entries in the roster. An unfiled entry is
+     * an entry that doesn't belong to any groups.
+     *
+     * @return the number of unfiled entries in the roster.
+     */
+    public int getUnfiledEntryCount() {
+        return unfiledEntries.size();
+    }
+
+    /**
+     * Returns an unmodifiable collection for the unfiled roster entries. An unfiled entry is
+     * an entry that doesn't belong to any groups.
+     *
+     * @return the unfiled roster entries.
+     */
+    public Collection<RosterEntry> getUnfiledEntries() {
+        return Collections.unmodifiableList(unfiledEntries);
+    }
+
+    /**
+     * Returns the roster entry associated with the given XMPP address or
+     * <tt>null</tt> if the user is not an entry in the roster.
+     *
+     * @param user the XMPP address of the user (eg "jsmith@example.com"). The address could be
+     *             in any valid format (e.g. "domain/resource", "user@domain" or "user@domain/resource").
+     * @return the roster entry or <tt>null</tt> if it does not exist.
+     */
+    public RosterEntry getEntry(String user) {
+        if (user == null) {
+            return null;
+        }
+        return entries.get(user.toLowerCase());
+    }
+
+    /**
+     * Returns true if the specified XMPP address is an entry in the roster.
+     *
+     * @param user the XMPP address of the user (eg "jsmith@example.com"). The
+     *             address could be in any valid format (e.g. "domain/resource",
+     *             "user@domain" or "user@domain/resource").
+     * @return true if the XMPP address is an entry in the roster.
+     */
+    public boolean contains(String user) {
+        return getEntry(user) != null;
+    }
+
+    /**
+     * Returns the roster group with the specified name, or <tt>null</tt> if the
+     * group doesn't exist.
+     *
+     * @param name the name of the group.
+     * @return the roster group with the specified name.
+     */
+    public RosterGroup getGroup(String name) {
+        return groups.get(name);
+    }
+
+    /**
+     * Returns the number of the groups in the roster.
+     *
+     * @return the number of groups in the roster.
+     */
+    public int getGroupCount() {
+        return groups.size();
+    }
+
+    /**
+     * Returns an unmodifiable collections of all the roster groups.
+     *
+     * @return an iterator for all roster groups.
+     */
+    public Collection<RosterGroup> getGroups() {
+        return Collections.unmodifiableCollection(groups.values());
+    }
+
+    /**
+     * Returns the presence info for a particular user. If the user is offline, or
+     * if no presence data is available (such as when you are not subscribed to the
+     * user's presence updates), unavailable presence will be returned.<p>
+     * <p/>
+     * If the user has several presences (one for each resource), then the presence with
+     * highest priority will be returned. If multiple presences have the same priority,
+     * the one with the "most available" presence mode will be returned. In order,
+     * that's {@link org.jivesoftware.smack.packet.Presence.Mode#chat free to chat},
+     * {@link org.jivesoftware.smack.packet.Presence.Mode#available available},
+     * {@link org.jivesoftware.smack.packet.Presence.Mode#away away},
+     * {@link org.jivesoftware.smack.packet.Presence.Mode#xa extended away}, and
+     * {@link org.jivesoftware.smack.packet.Presence.Mode#dnd do not disturb}.<p>
+     * <p/>
+     * Note that presence information is received asynchronously. So, just after logging
+     * in to the server, presence values for users in the roster may be unavailable
+     * even if they are actually online. In other words, the value returned by this
+     * method should only be treated as a snapshot in time, and may not accurately reflect
+     * other user's presence instant by instant. If you need to track presence over time,
+     * such as when showing a visual representation of the roster, consider using a
+     * {@link RosterListener}.
+     *
+     * @param user an XMPP ID. The address could be in any valid format (e.g.
+     *             "domain/resource", "user@domain" or "user@domain/resource"). Any resource
+     *             information that's part of the ID will be discarded.
+     * @return the user's current presence, or unavailable presence if the user is offline
+     *         or if no presence information is available..
+     */
+    public Presence getPresence(String user) {
+        String key = getPresenceMapKey(StringUtils.parseBareAddress(user));
+        Map<String, Presence> userPresences = presenceMap.get(key);
+        if (userPresences == null) {
+            Presence presence = new Presence(Presence.Type.unavailable);
+            presence.setFrom(user);
+            return presence;
+        }
+        else {
+            // Find the resource with the highest priority
+            // Might be changed to use the resource with the highest availability instead.
+            Presence presence = null;
+
+            for (String resource : userPresences.keySet()) {
+                Presence p = userPresences.get(resource);
+                if (!p.isAvailable()) {
+                    continue;
+                }
+                // Chose presence with highest priority first.
+                if (presence == null || p.getPriority() > presence.getPriority()) {
+                    presence = p;
+                }
+                // If equal priority, choose "most available" by the mode value.
+                else if (p.getPriority() == presence.getPriority()) {
+                    Presence.Mode pMode = p.getMode();
+                    // Default to presence mode of available.
+                    if (pMode == null) {
+                        pMode = Presence.Mode.available;
+                    }
+                    Presence.Mode presenceMode = presence.getMode();
+                    // Default to presence mode of available.
+                    if (presenceMode == null) {
+                        presenceMode = Presence.Mode.available;
+                    }
+                    if (pMode.compareTo(presenceMode) < 0) {
+                        presence = p;
+                    }
+                }
+            }
+            if (presence == null) {
+                presence = new Presence(Presence.Type.unavailable);
+                presence.setFrom(user);
+                return presence;
+            }
+            else {
+                return presence;
+            }
+        }
+    }
+
+    /**
+     * Returns the presence info for a particular user's resource, or unavailable presence
+     * if the user is offline or if no presence information is available, such as
+     * when you are not subscribed to the user's presence updates.
+     *
+     * @param userWithResource a fully qualified XMPP ID including a resource (user@domain/resource).
+     * @return the user's current presence, or unavailable presence if the user is offline
+     *         or if no presence information is available.
+     */
+    public Presence getPresenceResource(String userWithResource) {
+        String key = getPresenceMapKey(userWithResource);
+        String resource = StringUtils.parseResource(userWithResource);
+        Map<String, Presence> userPresences = presenceMap.get(key);
+        if (userPresences == null) {
+            Presence presence = new Presence(Presence.Type.unavailable);
+            presence.setFrom(userWithResource);
+            return presence;
+        }
+        else {
+            Presence presence = userPresences.get(resource);
+            if (presence == null) {
+                presence = new Presence(Presence.Type.unavailable);
+                presence.setFrom(userWithResource);
+                return presence;
+            }
+            else {
+                return presence;
+            }
+        }
+    }
+
+    /**
+     * Returns an iterator (of Presence objects) for all of a user's current presences
+     * or an unavailable presence if the user is unavailable (offline) or if no presence
+     * information is available, such as when you are not subscribed to the user's presence
+     * updates.
+     *
+     * @param user a XMPP ID, e.g. jdoe@example.com.
+     * @return an iterator (of Presence objects) for all the user's current presences,
+     *         or an unavailable presence if the user is offline or if no presence information
+     *         is available.
+     */
+    public Iterator<Presence> getPresences(String user) {
+        String key = getPresenceMapKey(user);
+        Map<String, Presence> userPresences = presenceMap.get(key);
+        if (userPresences == null) {
+            Presence presence = new Presence(Presence.Type.unavailable);
+            presence.setFrom(user);
+            return Arrays.asList(presence).iterator();
+        }
+        else {
+            Collection<Presence> answer = new ArrayList<Presence>();
+            for (Presence presence : userPresences.values()) {
+                if (presence.isAvailable()) {
+                    answer.add(presence);
+                }
+            }
+            if (!answer.isEmpty()) {
+                return answer.iterator();
+            }
+            else {
+                Presence presence = new Presence(Presence.Type.unavailable);
+                presence.setFrom(user);
+                return Arrays.asList(presence).iterator();    
+            }
+        }
+    }
+
+    /**
+     * Cleans up all resources used by the roster.
+     */
+    void cleanup() {
+        rosterListeners.clear();
+    }
+
+    /**
+     * Returns the key to use in the presenceMap for a fully qualified XMPP ID.
+     * The roster can contain any valid address format such us "domain/resource",
+     * "user@domain" or "user@domain/resource". If the roster contains an entry
+     * associated with the fully qualified XMPP ID then use the fully qualified XMPP
+     * ID as the key in presenceMap, otherwise use the bare address. Note: When the
+     * key in presenceMap is a fully qualified XMPP ID, the userPresences is useless
+     * since it will always contain one entry for the user.
+     *
+     * @param user the bare or fully qualified XMPP ID, e.g. jdoe@example.com or
+     *             jdoe@example.com/Work.
+     * @return the key to use in the presenceMap for the fully qualified XMPP ID.
+     */
+    private String getPresenceMapKey(String user) {
+        if (user == null) {
+            return null;
+        }
+        String key = user;
+        if (!contains(user)) {
+            key = StringUtils.parseBareAddress(user);
+        }
+        return key.toLowerCase();
+    }
+
+    /**
+     * Changes the presence of available contacts offline by simulating an unavailable
+     * presence sent from the server. After a disconnection, every Presence is set
+     * to offline.
+     */
+    private void setOfflinePresences() {
+        Presence packetUnavailable;
+        for (String user : presenceMap.keySet()) {
+            Map<String, Presence> resources = presenceMap.get(user);
+            if (resources != null) {
+                for (String resource : resources.keySet()) {
+                    packetUnavailable = new Presence(Presence.Type.unavailable);
+                    packetUnavailable.setFrom(user + "/" + resource);
+                    presencePacketListener.processPacket(packetUnavailable);
+                }
+            }
+        }
+    }
+
+    /**
+     * Fires roster changed event to roster listeners indicating that the
+     * specified collections of contacts have been added, updated or deleted
+     * from the roster.
+     *
+     * @param addedEntries   the collection of address of the added contacts.
+     * @param updatedEntries the collection of address of the updated contacts.
+     * @param deletedEntries the collection of address of the deleted contacts.
+     */
+    private void fireRosterChangedEvent(Collection<String> addedEntries, Collection<String> updatedEntries,
+            Collection<String> deletedEntries) {
+        for (RosterListener listener : rosterListeners) {
+            if (!addedEntries.isEmpty()) {
+                listener.entriesAdded(addedEntries);
+            }
+            if (!updatedEntries.isEmpty()) {
+                listener.entriesUpdated(updatedEntries);
+            }
+            if (!deletedEntries.isEmpty()) {
+                listener.entriesDeleted(deletedEntries);
+            }
+        }
+    }
+
+    /**
+     * Fires roster presence changed event to roster listeners.
+     *
+     * @param presence the presence change.
+     */
+    private void fireRosterPresenceEvent(Presence presence) {
+        for (RosterListener listener : rosterListeners) {
+            listener.presenceChanged(presence);
+        }
+    }
+
+    /**
+     * An enumeration for the subscription mode options.
+     */
+    public enum SubscriptionMode {
+
+        /**
+         * Automatically accept all subscription and unsubscription requests. This is
+         * the default mode and is suitable for simple client. More complex client will
+         * likely wish to handle subscription requests manually.
+         */
+        accept_all,
+
+        /**
+         * Automatically reject all subscription requests.
+         */
+        reject_all,
+
+        /**
+         * Subscription requests are ignored, which means they must be manually
+         * processed by registering a listener for presence packets and then looking
+         * for any presence requests that have the type Presence.Type.SUBSCRIBE or
+         * Presence.Type.UNSUBSCRIBE.
+         */
+        manual
+    }
+
+    /**
+     * Listens for all presence packets and processes them.
+     */
+    private class PresencePacketListener implements PacketListener {
+
+        public void processPacket(Packet packet) {
+            Presence presence = (Presence) packet;
+            String from = presence.getFrom();
+            String key = getPresenceMapKey(from);
+
+            // If an "available" presence, add it to the presence map. Each presence
+            // map will hold for a particular user a map with the presence
+            // packets saved for each resource.
+            if (presence.getType() == Presence.Type.available) {
+                Map<String, Presence> userPresences;
+                // Get the user presence map
+                if (presenceMap.get(key) == null) {
+                    userPresences = new ConcurrentHashMap<String, Presence>();
+                    presenceMap.put(key, userPresences);
+                }
+                else {
+                    userPresences = presenceMap.get(key);
+                }
+                // See if an offline presence was being stored in the map. If so, remove
+                // it since we now have an online presence.
+                userPresences.remove("");
+                // Add the new presence, using the resources as a key.
+                userPresences.put(StringUtils.parseResource(from), presence);
+                // If the user is in the roster, fire an event.
+                RosterEntry entry = entries.get(key);
+                if (entry != null) {
+                    fireRosterPresenceEvent(presence);
+                }
+            }
+            // If an "unavailable" packet.
+            else if (presence.getType() == Presence.Type.unavailable) {
+                // If no resource, this is likely an offline presence as part of
+                // a roster presence flood. In that case, we store it.
+                if ("".equals(StringUtils.parseResource(from))) {
+                    Map<String, Presence> userPresences;
+                    // Get the user presence map
+                    if (presenceMap.get(key) == null) {
+                        userPresences = new ConcurrentHashMap<String, Presence>();
+                        presenceMap.put(key, userPresences);
+                    }
+                    else {
+                        userPresences = presenceMap.get(key);
+                    }
+                    userPresences.put("", presence);
+                }
+                // Otherwise, this is a normal offline presence.
+                else if (presenceMap.get(key) != null) {
+                    Map<String, Presence> userPresences = presenceMap.get(key);
+                    // Store the offline presence, as it may include extra information
+                    // such as the user being on vacation.
+                    userPresences.put(StringUtils.parseResource(from), presence);
+                }
+                // If the user is in the roster, fire an event.
+                RosterEntry entry = entries.get(key);
+                if (entry != null) {
+                    fireRosterPresenceEvent(presence);
+                }
+            }
+            else if (presence.getType() == Presence.Type.subscribe) {
+                if (subscriptionMode == SubscriptionMode.accept_all) {
+                    // Accept all subscription requests.
+                    Presence response = new Presence(Presence.Type.subscribed);
+                    response.setTo(presence.getFrom());
+                    connection.sendPacket(response);
+                }
+                else if (subscriptionMode == SubscriptionMode.reject_all) {
+                    // Reject all subscription requests.
+                    Presence response = new Presence(Presence.Type.unsubscribed);
+                    response.setTo(presence.getFrom());
+                    connection.sendPacket(response);
+                }
+                // Otherwise, in manual mode so ignore.
+            }
+            else if (presence.getType() == Presence.Type.unsubscribe) {
+                if (subscriptionMode != SubscriptionMode.manual) {
+                    // Acknowledge and accept unsubscription notification so that the
+                    // server will stop sending notifications saying that the contact
+                    // has unsubscribed to our presence.
+                    Presence response = new Presence(Presence.Type.unsubscribed);
+                    response.setTo(presence.getFrom());
+                    connection.sendPacket(response);
+                }
+                // Otherwise, in manual mode so ignore.
+            }
+            // Error presence packets from a bare JID mean we invalidate all existing
+            // presence info for the user.
+            else if (presence.getType() == Presence.Type.error &&
+                    "".equals(StringUtils.parseResource(from)))
+            {
+                Map<String, Presence> userPresences;
+                if (!presenceMap.containsKey(key)) {
+                    userPresences = new ConcurrentHashMap<String, Presence>();
+                    presenceMap.put(key, userPresences);
+                }
+                else {
+                    userPresences = presenceMap.get(key);
+                    // Any other presence data is invalidated by the error packet.
+                    userPresences.clear();
+                }
+                // Set the new presence using the empty resource as a key.
+                userPresences.put("", presence);
+                // If the user is in the roster, fire an event.
+                RosterEntry entry = entries.get(key);
+                if (entry != null) {
+                    fireRosterPresenceEvent(presence);
+                }
+            }
+        }
+    }
+    
+    /**
+     * Listen for empty IQ results which indicate that the client has already a current
+     * roster version
+     * @author Till Klocke
+     *
+     */
+    
+    private class RosterResultListener implements PacketListener{
+
+		public void processPacket(Packet packet) {
+			if(packet instanceof IQ){
+				IQ result = (IQ)packet;
+				if(result.getType().equals(IQ.Type.RESULT) && result.getExtensions().isEmpty()){
+					Collection<String> addedEntries = new ArrayList<String>();
+		            Collection<String> updatedEntries = new ArrayList<String>();
+		            Collection<String> deletedEntries = new ArrayList<String>();
+		            if(persistentStorage!=null){
+		            	for(RosterPacket.Item item : persistentStorage.getEntries()){
+		            		insertRosterItem(item,addedEntries,updatedEntries,deletedEntries);
+		            	}
+                            }
+		            synchronized (Roster.this) {
+		                rosterInitialized = true;
+		                Roster.this.notifyAll();
+		            }
+		            fireRosterChangedEvent(addedEntries,updatedEntries,deletedEntries);
+			    }
+			}
+			connection.removePacketListener(this);
+		}
+    }
+
+    /**
+     * Listens for all roster packets and processes them.
+     */
+    private class RosterPacketListener implements PacketListener {
+
+        public void processPacket(Packet packet) {
+            // Keep a registry of the entries that were added, deleted or updated. An event
+            // will be fired for each affected entry
+            Collection<String> addedEntries = new ArrayList<String>();
+            Collection<String> updatedEntries = new ArrayList<String>();
+            Collection<String> deletedEntries = new ArrayList<String>();
+           
+            String version=null;
+            RosterPacket rosterPacket = (RosterPacket) packet;
+            List<RosterPacket.Item> rosterItems = new ArrayList<RosterPacket.Item>();
+            for(RosterPacket.Item item : rosterPacket.getRosterItems()){
+            	rosterItems.add(item);
+            }
+            //Here we check if the server send a versioned roster, if not we do not use
+            //the roster storage to store entries and work like in the old times 
+            if(rosterPacket.getVersion()==null){
+            	persistentStorage=null;
+            } else{
+            	version = rosterPacket.getVersion();
+            }
+            
+            if(persistentStorage!=null && !rosterInitialized){
+            	for(RosterPacket.Item item : persistentStorage.getEntries()){
+            		rosterItems.add(item);
+            	}
+            }
+            
+            for (RosterPacket.Item item : rosterItems) {
+            	insertRosterItem(item,addedEntries,updatedEntries,deletedEntries);
+            }
+            if(persistentStorage!=null){
+            	for (RosterPacket.Item i : rosterPacket.getRosterItems()){
+            		if(i.getItemType().equals(RosterPacket.ItemType.remove)){
+            			persistentStorage.removeEntry(i.getUser());
+            		}
+            		else{
+            			persistentStorage.addEntry(i, version);
+            		}
+            	}
+            }
+            // Mark the roster as initialized.
+            synchronized (Roster.this) {
+                rosterInitialized = true;
+                Roster.this.notifyAll();
+            }
+
+            // Fire event for roster listeners.
+            fireRosterChangedEvent(addedEntries, updatedEntries, deletedEntries);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/RosterEntry.java b/src/org/jivesoftware/smack/RosterEntry.java
new file mode 100644
index 0000000..55b394e
--- /dev/null
+++ b/src/org/jivesoftware/smack/RosterEntry.java
@@ -0,0 +1,244 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.RosterPacket;
+
+import java.util.*;
+
+/**
+ * Each user in your roster is represented by a roster entry, which contains the user's
+ * JID and a name or nickname you assign.
+ *
+ * @author Matt Tucker
+ */
+public class RosterEntry {
+
+    private String user;
+    private String name;
+    private RosterPacket.ItemType type;
+    private RosterPacket.ItemStatus status;
+    final private Roster roster;
+    final private Connection connection;
+
+    /**
+     * Creates a new roster entry.
+     *
+     * @param user the user.
+     * @param name the nickname for the entry.
+     * @param type the subscription type.
+     * @param status the subscription status (related to subscriptions pending to be approbed).
+     * @param connection a connection to the XMPP server.
+     */
+    RosterEntry(String user, String name, RosterPacket.ItemType type,
+                RosterPacket.ItemStatus status, Roster roster, Connection connection) {
+        this.user = user;
+        this.name = name;
+        this.type = type;
+        this.status = status;
+        this.roster = roster;
+        this.connection = connection;
+    }
+
+    /**
+     * Returns the JID of the user associated with this entry.
+     *
+     * @return the user associated with this entry.
+     */
+    public String getUser() {
+        return user;
+    }
+
+    /**
+     * Returns the name associated with this entry.
+     *
+     * @return the name.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Sets the name associated with this entry.
+     *
+     * @param name the name.
+     */
+    public void setName(String name) {
+        // Do nothing if the name hasn't changed.
+        if (name != null && name.equals(this.name)) {
+            return;
+        }
+        this.name = name;
+        RosterPacket packet = new RosterPacket();
+        packet.setType(IQ.Type.SET);
+        packet.addRosterItem(toRosterItem(this));
+        connection.sendPacket(packet);
+    }
+
+    /**
+     * Updates the state of the entry with the new values.
+     *
+     * @param name the nickname for the entry.
+     * @param type the subscription type.
+     * @param status the subscription status (related to subscriptions pending to be approbed).
+     */
+    void updateState(String name, RosterPacket.ItemType type, RosterPacket.ItemStatus status) {
+        this.name = name;
+        this.type = type;
+        this.status = status;
+    }
+
+    /**
+     * Returns an unmodifiable collection of the roster groups that this entry belongs to.
+     *
+     * @return an iterator for the groups this entry belongs to.
+     */
+    public Collection<RosterGroup> getGroups() {
+        List<RosterGroup> results = new ArrayList<RosterGroup>();
+        // Loop through all roster groups and find the ones that contain this
+        // entry. This algorithm should be fine
+        for (RosterGroup group: roster.getGroups()) {
+            if (group.contains(this)) {
+                results.add(group);
+            }
+        }
+        return Collections.unmodifiableCollection(results);
+    }
+
+    /**
+     * Returns the roster subscription type of the entry. When the type is
+     * RosterPacket.ItemType.none or RosterPacket.ItemType.from,
+     * refer to {@link RosterEntry getStatus()} to see if a subscription request
+     * is pending.
+     *
+     * @return the type.
+     */
+    public RosterPacket.ItemType getType() {
+        return type;
+    }
+
+    /**
+     * Returns the roster subscription status of the entry. When the status is
+     * RosterPacket.ItemStatus.SUBSCRIPTION_PENDING, the contact has to answer the
+     * subscription request.
+     *
+     * @return the status.
+     */
+    public RosterPacket.ItemStatus getStatus() {
+        return status;
+    }
+
+    public String toString() {
+        StringBuilder buf = new StringBuilder();
+        if (name != null) {
+            buf.append(name).append(": ");
+        }
+        buf.append(user);
+        Collection<RosterGroup> groups = getGroups();
+        if (!groups.isEmpty()) {
+            buf.append(" [");
+            Iterator<RosterGroup> iter = groups.iterator();
+            RosterGroup group = iter.next();
+            buf.append(group.getName());
+            while (iter.hasNext()) {
+            buf.append(", ");
+                group = iter.next();
+                buf.append(group.getName());
+            }
+            buf.append("]");
+        }
+        return buf.toString();
+    }
+
+    public boolean equals(Object object) {
+        if (this == object) {
+            return true;
+        }
+        if (object != null && object instanceof RosterEntry) {
+            return user.equals(((RosterEntry)object).getUser());
+        }
+        else {
+            return false;
+        }
+    }
+
+    @Override
+    public int hashCode() {
+        return this.user.hashCode();
+    }
+
+    /**
+     * Indicates whether some other object is "equal to" this by comparing all members.
+     * <p>
+     * The {@link #equals(Object)} method returns <code>true</code> if the user JIDs are equal.
+     * 
+     * @param obj the reference object with which to compare.
+     * @return <code>true</code> if this object is the same as the obj argument; <code>false</code>
+     *         otherwise.
+     */
+    public boolean equalsDeep(Object obj) {
+        if (this == obj)
+            return true;
+        if (obj == null)
+            return false;
+        if (getClass() != obj.getClass())
+            return false;
+        RosterEntry other = (RosterEntry) obj;
+        if (name == null) {
+            if (other.name != null)
+                return false;
+        }
+        else if (!name.equals(other.name))
+            return false;
+        if (status == null) {
+            if (other.status != null)
+                return false;
+        }
+        else if (!status.equals(other.status))
+            return false;
+        if (type == null) {
+            if (other.type != null)
+                return false;
+        }
+        else if (!type.equals(other.type))
+            return false;
+        if (user == null) {
+            if (other.user != null)
+                return false;
+        }
+        else if (!user.equals(other.user))
+            return false;
+        return true;
+    }
+    
+    static RosterPacket.Item toRosterItem(RosterEntry entry) {
+        RosterPacket.Item item = new RosterPacket.Item(entry.getUser(), entry.getName());
+        item.setItemType(entry.getType());
+        item.setItemStatus(entry.getStatus());
+        // Set the correct group names for the item.
+        for (RosterGroup group : entry.getGroups()) {
+            item.addGroupName(group.getName());
+        }
+        return item;
+    }
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/RosterGroup.java b/src/org/jivesoftware/smack/RosterGroup.java
new file mode 100644
index 0000000..e768f6d
--- /dev/null
+++ b/src/org/jivesoftware/smack/RosterGroup.java
@@ -0,0 +1,253 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.RosterPacket;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * A group of roster entries.
+ *
+ * @see Roster#getGroup(String)
+ * @author Matt Tucker
+ */
+public class RosterGroup {
+
+    private String name;
+    private Connection connection;
+    private final List<RosterEntry> entries;
+
+    /**
+     * Creates a new roster group instance.
+     *
+     * @param name the name of the group.
+     * @param connection the connection the group belongs to.
+     */
+    RosterGroup(String name, Connection connection) {
+        this.name = name;
+        this.connection = connection;
+        entries = new ArrayList<RosterEntry>();
+    }
+
+    /**
+     * Returns the name of the group.
+     *
+     * @return the name of the group.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Sets the name of the group. Changing the group's name is like moving all the group entries
+     * of the group to a new group specified by the new name. Since this group won't have entries 
+     * it will be removed from the roster. This means that all the references to this object will 
+     * be invalid and will need to be updated to the new group specified by the new name.
+     *
+     * @param name the name of the group.
+     */
+    public void setName(String name) {
+        synchronized (entries) {
+            for (RosterEntry entry : entries) {
+                RosterPacket packet = new RosterPacket();
+                packet.setType(IQ.Type.SET);
+                RosterPacket.Item item = RosterEntry.toRosterItem(entry);
+                item.removeGroupName(this.name);
+                item.addGroupName(name);
+                packet.addRosterItem(item);
+                connection.sendPacket(packet);
+            }
+        }
+    }
+
+    /**
+     * Returns the number of entries in the group.
+     *
+     * @return the number of entries in the group.
+     */
+    public int getEntryCount() {
+        synchronized (entries) {
+            return entries.size();
+        }
+    }
+
+    /**
+     * Returns an unmodifiable collection of all entries in the group.
+     *
+     * @return all entries in the group.
+     */
+    public Collection<RosterEntry> getEntries() {
+        synchronized (entries) {
+            return Collections.unmodifiableList(new ArrayList<RosterEntry>(entries));
+        }
+    }
+
+    /**
+     * Returns the roster entry associated with the given XMPP address or
+     * <tt>null</tt> if the user is not an entry in the group.
+     *
+     * @param user the XMPP address of the user (eg "jsmith@example.com").
+     * @return the roster entry or <tt>null</tt> if it does not exist in the group.
+     */
+    public RosterEntry getEntry(String user) {
+        if (user == null) {
+            return null;
+        }
+        // Roster entries never include a resource so remove the resource
+        // if it's a part of the XMPP address.
+        user = StringUtils.parseBareAddress(user);
+        String userLowerCase = user.toLowerCase();
+        synchronized (entries) {
+            for (RosterEntry entry : entries) {
+                if (entry.getUser().equals(userLowerCase)) {
+                    return entry;
+                }
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns true if the specified entry is part of this group.
+     *
+     * @param entry a roster entry.
+     * @return true if the entry is part of this group.
+     */
+    public boolean contains(RosterEntry entry) {
+        synchronized (entries) {
+            return entries.contains(entry);
+        }
+    }
+
+    /**
+     * Returns true if the specified XMPP address is an entry in this group.
+     *
+     * @param user the XMPP address of the user.
+     * @return true if the XMPP address is an entry in this group.
+     */
+    public boolean contains(String user) {
+        return getEntry(user) != null;
+    }
+
+    /**
+     * Adds a roster entry to this group. If the entry was unfiled then it will be removed from 
+     * the unfiled list and will be added to this group.
+     * Note that this is an asynchronous call -- Smack must wait for the server
+     * to receive the updated roster.
+     *
+     * @param entry a roster entry.
+     * @throws XMPPException if an error occured while trying to add the entry to the group.
+     */
+    public void addEntry(RosterEntry entry) throws XMPPException {
+        PacketCollector collector = null;
+        // Only add the entry if it isn't already in the list.
+        synchronized (entries) {
+            if (!entries.contains(entry)) {
+                RosterPacket packet = new RosterPacket();
+                packet.setType(IQ.Type.SET);
+                RosterPacket.Item item = RosterEntry.toRosterItem(entry);
+                item.addGroupName(getName());
+                packet.addRosterItem(item);
+                // Wait up to a certain number of seconds for a reply from the server.
+                collector = connection
+                        .createPacketCollector(new PacketIDFilter(packet.getPacketID()));
+                connection.sendPacket(packet);
+            }
+        }
+        if (collector != null) {
+            IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+            collector.cancel();
+            if (response == null) {
+                throw new XMPPException("No response from the server.");
+            }
+            // If the server replied with an error, throw an exception.
+            else if (response.getType() == IQ.Type.ERROR) {
+                throw new XMPPException(response.getError());
+            }
+        }
+    }
+
+    /**
+     * Removes a roster entry from this group. If the entry does not belong to any other group 
+     * then it will be considered as unfiled, therefore it will be added to the list of unfiled 
+     * entries.
+     * Note that this is an asynchronous call -- Smack must wait for the server
+     * to receive the updated roster.
+     *
+     * @param entry a roster entry.
+     * @throws XMPPException if an error occured while trying to remove the entry from the group. 
+     */
+    public void removeEntry(RosterEntry entry) throws XMPPException {
+        PacketCollector collector = null;
+        // Only remove the entry if it's in the entry list.
+        // Remove the entry locally, if we wait for RosterPacketListenerprocess>>Packet(Packet)
+        // to take place the entry will exist in the group until a packet is received from the 
+        // server.
+        synchronized (entries) {
+            if (entries.contains(entry)) {
+                RosterPacket packet = new RosterPacket();
+                packet.setType(IQ.Type.SET);
+                RosterPacket.Item item = RosterEntry.toRosterItem(entry);
+                item.removeGroupName(this.getName());
+                packet.addRosterItem(item);
+                // Wait up to a certain number of seconds for a reply from the server.
+                collector = connection
+                        .createPacketCollector(new PacketIDFilter(packet.getPacketID()));
+                connection.sendPacket(packet);
+            }
+        }
+        if (collector != null) {
+            IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+            collector.cancel();
+            if (response == null) {
+                throw new XMPPException("No response from the server.");
+            }
+            // If the server replied with an error, throw an exception.
+            else if (response.getType() == IQ.Type.ERROR) {
+                throw new XMPPException(response.getError());
+            }
+        }
+    }
+
+    public void addEntryLocal(RosterEntry entry) {
+        // Only add the entry if it isn't already in the list.
+        synchronized (entries) {
+            entries.remove(entry);
+            entries.add(entry);
+        }
+    }
+
+    void removeEntryLocal(RosterEntry entry) {
+         // Only remove the entry if it's in the entry list.
+        synchronized (entries) {
+            if (entries.contains(entry)) {
+                entries.remove(entry);
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/RosterListener.java b/src/org/jivesoftware/smack/RosterListener.java
new file mode 100644
index 0000000..8be9ddc
--- /dev/null
+++ b/src/org/jivesoftware/smack/RosterListener.java
@@ -0,0 +1,83 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.Presence;
+
+import java.util.Collection;
+
+/**
+ * A listener that is fired any time a roster is changed or the presence of
+ * a user in the roster is changed.
+ * 
+ * @see Roster#addRosterListener(RosterListener)
+ * @author Matt Tucker
+ */
+public interface RosterListener {
+
+    /**
+     * Called when roster entries are added.
+     *
+     * @param addresses the XMPP addresses of the contacts that have been added to the roster.
+     */
+    public void entriesAdded(Collection<String> addresses);
+
+    /**
+     * Called when a roster entries are updated.
+     *
+     * @param addresses the XMPP addresses of the contacts whose entries have been updated.
+     */
+    public void entriesUpdated(Collection<String> addresses);
+
+    /**
+     * Called when a roster entries are removed.
+     *
+     * @param addresses the XMPP addresses of the contacts that have been removed from the roster.
+     */
+    public void entriesDeleted(Collection<String> addresses);
+
+    /**
+     * Called when the presence of a roster entry is changed. Care should be taken
+     * when using the presence data delivered as part of this event. Specifically,
+     * when a user account is online with multiple resources, the UI should account
+     * for that. For example, say a user is online with their desktop computer and
+     * mobile phone. If the user logs out of the IM client on their mobile phone, the
+     * user should not be shown in the roster (contact list) as offline since they're
+     * still available as another resource.<p>
+     *
+     * To get the current "best presence" for a user after the presence update, query the roster:
+     * <pre>
+     *    String user = presence.getFrom();
+     *    Presence bestPresence = roster.getPresence(user);
+     * </pre>
+     *
+     * That will return the presence value for the user with the highest priority and
+     * availability.
+     *
+     * Note that this listener is triggered for presence (mode) changes only
+     * (e.g presence of types available and unavailable. Subscription-related
+     * presence packets will not cause this method to be called.
+     *
+     * @param presence the presence that changed.
+     * @see Roster#getPresence(String)
+     */
+    public void presenceChanged(Presence presence);
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/RosterStorage.java b/src/org/jivesoftware/smack/RosterStorage.java
new file mode 100644
index 0000000..8c5f386
--- /dev/null
+++ b/src/org/jivesoftware/smack/RosterStorage.java
@@ -0,0 +1,54 @@
+package org.jivesoftware.smack;
+
+import java.util.List;
+
+import org.jivesoftware.smack.packet.RosterPacket;
+
+/**
+ * This is an interface for persistent roster storage needed to implement XEP-0237
+ * @author Till Klocke
+ *
+ */
+
+public interface RosterStorage {
+	
+	/**
+	 * This method returns a List object with all RosterEntries contained in this store.
+	 * @return List object with all entries in local roster storage
+	 */
+	public List<RosterPacket.Item> getEntries();
+	/**
+	 * This method returns the RosterEntry which belongs to a specific user.
+	 * @param bareJid The bare JID of the RosterEntry
+	 * @return The RosterEntry which belongs to that user
+	 */
+	public RosterPacket.Item getEntry(String bareJid);
+	/**
+	 * Returns the number of entries in this roster store
+	 * @return the number of entries
+	 */
+	public int getEntryCount();
+	/**
+	 * This methos returns the version number as specified by the "ver" attribute
+	 * of the local store. Should return an emtpy string if store is empty.
+	 * @return local roster version
+	 */
+	public String getRosterVersion();
+	/**
+	 * This method stores a new RosterEntry in this store or overrides an existing one.
+	 * If ver is null an IllegalArgumentException should be thrown.
+	 * @param entry the entry to save
+	 * @param ver the version this roster push contained
+	 */
+	public void addEntry(RosterPacket.Item item, String ver);
+	/**
+	 * Removes an entry from the persistent storage
+	 * @param bareJid The bare JID of the entry to be removed
+	 */
+	public void removeEntry(String bareJid);
+	/**
+	 * Update an entry which has been modified locally
+	 * @param entry the entry to be updated
+	 */
+	public void updateLocalEntry(RosterPacket.Item item);
+}
diff --git a/src/org/jivesoftware/smack/SASLAuthentication.java b/src/org/jivesoftware/smack/SASLAuthentication.java
new file mode 100644
index 0000000..d7a7449
--- /dev/null
+++ b/src/org/jivesoftware/smack/SASLAuthentication.java
@@ -0,0 +1,586 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.Bind;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Session;
+import org.jivesoftware.smack.sasl.*;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import java.io.IOException;
+import java.lang.reflect.Constructor;
+import java.util.*;
+
+/**
+ * <p>This class is responsible authenticating the user using SASL, binding the resource
+ * to the connection and establishing a session with the server.</p>
+ *
+ * <p>Once TLS has been negotiated (i.e. the connection has been secured) it is possible to
+ * register with the server, authenticate using Non-SASL or authenticate using SASL. If the
+ * server supports SASL then Smack will first try to authenticate using SASL. But if that
+ * fails then Non-SASL will be tried.</p>
+ *
+ * <p>The server may support many SASL mechanisms to use for authenticating. Out of the box
+ * Smack provides several SASL mechanisms, but it is possible to register new SASL Mechanisms. Use
+ * {@link #registerSASLMechanism(String, Class)} to register a new mechanisms. A registered
+ * mechanism wont be used until {@link #supportSASLMechanism(String, int)} is called. By default,
+ * the list of supported SASL mechanisms is determined from the {@link SmackConfiguration}. </p>
+ *
+ * <p>Once the user has been authenticated with SASL, it is necessary to bind a resource for
+ * the connection. If no resource is passed in {@link #authenticate(String, String, String)}
+ * then the server will assign a resource for the connection. In case a resource is passed
+ * then the server will receive the desired resource but may assign a modified resource for
+ * the connection.</p>
+ *
+ * <p>Once a resource has been binded and if the server supports sessions then Smack will establish
+ * a session so that instant messaging and presence functionalities may be used.</p>
+ *
+ * @see org.jivesoftware.smack.sasl.SASLMechanism
+ *
+ * @author Gaston Dombiak
+ * @author Jay Kline
+ */
+public class SASLAuthentication implements UserAuthentication {
+
+    private static Map<String, Class<? extends SASLMechanism>> implementedMechanisms = new HashMap<String, Class<? extends SASLMechanism>>();
+    private static List<String> mechanismsPreferences = new ArrayList<String>();
+
+    private Connection connection;
+    private Collection<String> serverMechanisms = new ArrayList<String>();
+    private SASLMechanism currentMechanism = null;
+    /**
+     * Boolean indicating if SASL negotiation has finished and was successful.
+     */
+    private boolean saslNegotiated;
+    /**
+     * Boolean indication if SASL authentication has failed. When failed the server may end
+     * the connection.
+     */
+    private boolean saslFailed;
+    private boolean resourceBinded;
+    private boolean sessionSupported;
+    /**
+     * The SASL related error condition if there was one provided by the server.
+     */
+    private String errorCondition;
+
+    static {
+
+        // Register SASL mechanisms supported by Smack
+        registerSASLMechanism("EXTERNAL", SASLExternalMechanism.class);
+        registerSASLMechanism("GSSAPI", SASLGSSAPIMechanism.class);
+        registerSASLMechanism("DIGEST-MD5", SASLDigestMD5Mechanism.class);
+        registerSASLMechanism("CRAM-MD5", SASLCramMD5Mechanism.class);
+        registerSASLMechanism("PLAIN", SASLPlainMechanism.class);
+        registerSASLMechanism("ANONYMOUS", SASLAnonymous.class);
+
+//        supportSASLMechanism("GSSAPI",0);
+        supportSASLMechanism("DIGEST-MD5",0);
+//        supportSASLMechanism("CRAM-MD5",2);
+        supportSASLMechanism("PLAIN",1);
+        supportSASLMechanism("ANONYMOUS",2);
+
+    }
+
+    /**
+     * Registers a new SASL mechanism
+     *
+     * @param name   common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     * @param mClass a SASLMechanism subclass.
+     */
+    public static void registerSASLMechanism(String name, Class<? extends SASLMechanism> mClass) {
+        implementedMechanisms.put(name, mClass);
+    }
+
+    /**
+     * Unregisters an existing SASL mechanism. Once the mechanism has been unregistered it won't
+     * be possible to authenticate users using the removed SASL mechanism. It also removes the
+     * mechanism from the supported list.
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void unregisterSASLMechanism(String name) {
+        implementedMechanisms.remove(name);
+        mechanismsPreferences.remove(name);
+    }
+
+
+    /**
+     * Registers a new SASL mechanism in the specified preference position. The client will try
+     * to authenticate using the most prefered SASL mechanism that is also supported by the server.
+     * The SASL mechanism must be registered via {@link #registerSASLMechanism(String, Class)}
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void supportSASLMechanism(String name) {
+        mechanismsPreferences.add(0, name);
+    }
+
+    /**
+     * Registers a new SASL mechanism in the specified preference position. The client will try
+     * to authenticate using the most prefered SASL mechanism that is also supported by the server.
+     * Use the <tt>index</tt> parameter to set the level of preference of the new SASL mechanism.
+     * A value of 0 means that the mechanism is the most prefered one. The SASL mechanism must be
+     * registered via {@link #registerSASLMechanism(String, Class)}
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     * @param index preference position amongst all the implemented SASL mechanism. Starts with 0.
+     */
+    public static void supportSASLMechanism(String name, int index) {
+        mechanismsPreferences.add(index, name);
+    }
+
+    /**
+     * Un-supports an existing SASL mechanism. Once the mechanism has been unregistered it won't
+     * be possible to authenticate users using the removed SASL mechanism. Note that the mechanism
+     * is still registered, but will just not be used.
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void unsupportSASLMechanism(String name) {
+        mechanismsPreferences.remove(name);
+    }
+
+    /**
+     * Returns the registerd SASLMechanism classes sorted by the level of preference.
+     *
+     * @return the registerd SASLMechanism classes sorted by the level of preference.
+     */
+    public static List<Class<? extends SASLMechanism>> getRegisterSASLMechanisms() {
+        List<Class<? extends SASLMechanism>> answer = new ArrayList<Class<? extends SASLMechanism>>();
+        for (String mechanismsPreference : mechanismsPreferences) {
+            answer.add(implementedMechanisms.get(mechanismsPreference));
+        }
+        return answer;
+    }
+
+    SASLAuthentication(Connection connection) {
+        super();
+        this.connection = connection;
+        this.init();
+    }
+
+    /**
+     * Returns true if the server offered ANONYMOUS SASL as a way to authenticate users.
+     *
+     * @return true if the server offered ANONYMOUS SASL as a way to authenticate users.
+     */
+    public boolean hasAnonymousAuthentication() {
+        return serverMechanisms.contains("ANONYMOUS");
+    }
+
+    /**
+     * Returns true if the server offered SASL authentication besides ANONYMOUS SASL.
+     *
+     * @return true if the server offered SASL authentication besides ANONYMOUS SASL.
+     */
+    public boolean hasNonAnonymousAuthentication() {
+        return !serverMechanisms.isEmpty() && (serverMechanisms.size() != 1 || !hasAnonymousAuthentication());
+    }
+
+    /**
+     * Performs SASL authentication of the specified user. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server may assign a full JID with a username or resource different than the requested
+     * by this method.
+     *
+     * @param username the username that is authenticating with the server.
+     * @param resource the desired resource.
+     * @param cbh the CallbackHandler used to get information from the user
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticate(String username, String resource, CallbackHandler cbh) 
+            throws XMPPException {
+        // Locate the SASLMechanism to use
+        String selectedMechanism = null;
+        for (String mechanism : mechanismsPreferences) {
+            if (implementedMechanisms.containsKey(mechanism) &&
+                    serverMechanisms.contains(mechanism)) {
+                selectedMechanism = mechanism;
+                break;
+            }
+        }
+        if (selectedMechanism != null) {
+            // A SASL mechanism was found. Authenticate using the selected mechanism and then
+            // proceed to bind a resource
+            try {
+                Class<? extends SASLMechanism> mechanismClass = implementedMechanisms.get(selectedMechanism);
+                Constructor<? extends SASLMechanism> constructor = mechanismClass.getConstructor(SASLAuthentication.class);
+                currentMechanism = constructor.newInstance(this);
+                // Trigger SASL authentication with the selected mechanism. We use
+                // connection.getHost() since GSAPI requires the FQDN of the server, which
+                // may not match the XMPP domain.
+                currentMechanism.authenticate(username, connection.getHost(), cbh);
+
+                // Wait until SASL negotiation finishes
+                synchronized (this) {
+                    if (!saslNegotiated && !saslFailed) {
+                        try {
+                            wait(30000);
+                        }
+                        catch (InterruptedException e) {
+                            // Ignore
+                        }
+                    }
+                }
+
+                if (saslFailed) {
+                    // SASL authentication failed and the server may have closed the connection
+                    // so throw an exception
+                    if (errorCondition != null) {
+                        throw new XMPPException("SASL authentication " +
+                                selectedMechanism + " failed: " + errorCondition);
+                    }
+                    else {
+                        throw new XMPPException("SASL authentication failed using mechanism " +
+                                selectedMechanism);
+                    }
+                }
+
+                if (saslNegotiated) {
+                    // Bind a resource for this connection and
+                    return bindResourceAndEstablishSession(resource);
+                } else {
+                    // SASL authentication failed
+                }
+            }
+            catch (XMPPException e) {
+                throw e;
+            }
+            catch (Exception e) {
+                e.printStackTrace();
+            }
+        }
+        else {
+            throw new XMPPException("SASL Authentication failed. No known authentication mechanisims.");
+        }
+        throw new XMPPException("SASL authentication failed");
+    }
+
+    /**
+     * Performs SASL authentication of the specified user. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server may assign a full JID with a username or resource different than the requested
+     * by this method.
+     *
+     * @param username the username that is authenticating with the server.
+     * @param password the password to send to the server.
+     * @param resource the desired resource.
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticate(String username, String password, String resource)
+            throws XMPPException {
+        // Locate the SASLMechanism to use
+        String selectedMechanism = null;
+        for (String mechanism : mechanismsPreferences) {
+            if (implementedMechanisms.containsKey(mechanism) &&
+                    serverMechanisms.contains(mechanism)) {
+                selectedMechanism = mechanism;
+                break;
+            }
+        }
+        if (selectedMechanism != null) {
+            // A SASL mechanism was found. Authenticate using the selected mechanism and then
+            // proceed to bind a resource
+            try {
+                Class<? extends SASLMechanism> mechanismClass = implementedMechanisms.get(selectedMechanism);
+                Constructor<? extends SASLMechanism> constructor = mechanismClass.getConstructor(SASLAuthentication.class);
+                currentMechanism = constructor.newInstance(this);
+                // Trigger SASL authentication with the selected mechanism. We use
+                // connection.getHost() since GSAPI requires the FQDN of the server, which
+                // may not match the XMPP domain.
+                currentMechanism.authenticate(username, connection.getServiceName(), password);
+
+                // Wait until SASL negotiation finishes
+                synchronized (this) {
+                    if (!saslNegotiated && !saslFailed) {
+                        try {
+                            wait(30000);
+                        }
+                        catch (InterruptedException e) {
+                            // Ignore
+                        }
+                    }
+                }
+
+                if (saslFailed) {
+                    // SASL authentication failed and the server may have closed the connection
+                    // so throw an exception
+                    if (errorCondition != null) {
+                        throw new XMPPException("SASL authentication " +
+                                selectedMechanism + " failed: " + errorCondition);
+                    }
+                    else {
+                        throw new XMPPException("SASL authentication failed using mechanism " +
+                                selectedMechanism);
+                    }
+                }
+
+                if (saslNegotiated) {
+                    // Bind a resource for this connection and
+                    return bindResourceAndEstablishSession(resource);
+                }
+                else {
+                    // SASL authentication failed so try a Non-SASL authentication
+                    return new NonSASLAuthentication(connection)
+                            .authenticate(username, password, resource);
+                }
+            }
+            catch (XMPPException e) {
+                throw e;
+            }
+            catch (Exception e) {
+                e.printStackTrace();
+                // SASL authentication failed so try a Non-SASL authentication
+                return new NonSASLAuthentication(connection)
+                        .authenticate(username, password, resource);
+            }
+        }
+        else {
+            // No SASL method was found so try a Non-SASL authentication
+            return new NonSASLAuthentication(connection).authenticate(username, password, resource);
+        }
+    }
+
+    /**
+     * Performs ANONYMOUS SASL authentication. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server will assign a full JID with a randomly generated resource and possibly with
+     * no username.
+     *
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticateAnonymously() throws XMPPException {
+        try {
+            currentMechanism = new SASLAnonymous(this);
+            currentMechanism.authenticate(null,null,"");
+
+            // Wait until SASL negotiation finishes
+            synchronized (this) {
+                if (!saslNegotiated && !saslFailed) {
+                    try {
+                        wait(5000);
+                    }
+                    catch (InterruptedException e) {
+                        // Ignore
+                    }
+                }
+            }
+
+            if (saslFailed) {
+                // SASL authentication failed and the server may have closed the connection
+                // so throw an exception
+                if (errorCondition != null) {
+                    throw new XMPPException("SASL authentication failed: " + errorCondition);
+                }
+                else {
+                    throw new XMPPException("SASL authentication failed");
+                }
+            }
+
+            if (saslNegotiated) {
+                // Bind a resource for this connection and
+                return bindResourceAndEstablishSession(null);
+            }
+            else {
+                return new NonSASLAuthentication(connection).authenticateAnonymously();
+            }
+        } catch (IOException e) {
+            return new NonSASLAuthentication(connection).authenticateAnonymously();
+        }
+    }
+
+    private String bindResourceAndEstablishSession(String resource) throws XMPPException {
+        // Wait until server sends response containing the <bind> element
+        synchronized (this) {
+            if (!resourceBinded) {
+                try {
+                    wait(30000);
+                }
+                catch (InterruptedException e) {
+                    // Ignore
+                }
+            }
+        }
+
+        if (!resourceBinded) {
+            // Server never offered resource binding
+            throw new XMPPException("Resource binding not offered by server");
+        }
+
+        Bind bindResource = new Bind();
+        bindResource.setResource(resource);
+
+        PacketCollector collector = connection
+                .createPacketCollector(new PacketIDFilter(bindResource.getPacketID()));
+        // Send the packet
+        connection.sendPacket(bindResource);
+        // Wait up to a certain number of seconds for a response from the server.
+        Bind response = (Bind) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        String userJID = response.getJid();
+
+        if (sessionSupported) {
+            Session session = new Session();
+            collector = connection.createPacketCollector(new PacketIDFilter(session.getPacketID()));
+            // Send the packet
+            connection.sendPacket(session);
+            // Wait up to a certain number of seconds for a response from the server.
+            IQ ack = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+            collector.cancel();
+            if (ack == null) {
+                throw new XMPPException("No response from the server.");
+            }
+            // If the server replied with an error, throw an exception.
+            else if (ack.getType() == IQ.Type.ERROR) {
+                throw new XMPPException(ack.getError());
+            }
+        }
+        return userJID;
+    }
+
+    /**
+     * Sets the available SASL mechanism reported by the server. The server will report the
+     * available SASL mechanism once the TLS negotiation was successful. This information is
+     * stored and will be used when doing the authentication for logging in the user.
+     *
+     * @param mechanisms collection of strings with the available SASL mechanism reported
+     *                   by the server.
+     */
+    void setAvailableSASLMethods(Collection<String> mechanisms) {
+        this.serverMechanisms = mechanisms;
+    }
+
+    /**
+     * Returns true if the user was able to authenticate with the server usins SASL.
+     *
+     * @return true if the user was able to authenticate with the server usins SASL.
+     */
+    public boolean isAuthenticated() {
+        return saslNegotiated;
+    }
+
+    /**
+     * The server is challenging the SASL authentication we just sent. Forward the challenge
+     * to the current SASLMechanism we are using. The SASLMechanism will send a response to
+     * the server. The length of the challenge-response sequence varies according to the
+     * SASLMechanism in use.
+     *
+     * @param challenge a base64 encoded string representing the challenge.
+     * @throws IOException If a network error occures while authenticating.
+     */
+    void challengeReceived(String challenge) throws IOException {
+        currentMechanism.challengeReceived(challenge);
+    }
+
+    /**
+     * Notification message saying that SASL authentication was successful. The next step
+     * would be to bind the resource.
+     */
+    void authenticated() {
+        synchronized (this) {
+            saslNegotiated = true;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    /**
+     * Notification message saying that SASL authentication has failed. The server may have
+     * closed the connection depending on the number of possible retries.
+     * 
+     * @deprecated replaced by {@see #authenticationFailed(String)}.
+     */
+    void authenticationFailed() {
+        authenticationFailed(null);
+    }
+
+    /**
+     * Notification message saying that SASL authentication has failed. The server may have
+     * closed the connection depending on the number of possible retries.
+     * 
+     * @param condition the error condition provided by the server.
+     */
+    void authenticationFailed(String condition) {
+        synchronized (this) {
+            saslFailed = true;
+            errorCondition = condition;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    /**
+     * Notification message saying that the server requires the client to bind a
+     * resource to the stream.
+     */
+    void bindingRequired() {
+        synchronized (this) {
+            resourceBinded = true;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    public void send(Packet stanza) {
+        connection.sendPacket(stanza);
+    }
+
+    /**
+     * Notification message saying that the server supports sessions. When a server supports
+     * sessions the client needs to send a Session packet after successfully binding a resource
+     * for the session.
+     */
+    void sessionsSupported() {
+        sessionSupported = true;
+    }
+    
+    /**
+     * Initializes the internal state in order to be able to be reused. The authentication
+     * is used by the connection at the first login and then reused after the connection
+     * is disconnected and then reconnected.
+     */
+    protected void init() {
+        saslNegotiated = false;
+        saslFailed = false;
+        resourceBinded = false;
+        sessionSupported = false;
+    }
+}
diff --git a/src/org/jivesoftware/smack/SASLAuthentication.java.orig b/src/org/jivesoftware/smack/SASLAuthentication.java.orig
new file mode 100644
index 0000000..66ff693
--- /dev/null
+++ b/src/org/jivesoftware/smack/SASLAuthentication.java.orig
@@ -0,0 +1,586 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.Bind;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Session;
+import org.jivesoftware.smack.sasl.*;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import java.io.IOException;
+import java.lang.reflect.Constructor;
+import java.util.*;
+
+/**
+ * <p>This class is responsible authenticating the user using SASL, binding the resource
+ * to the connection and establishing a session with the server.</p>
+ *
+ * <p>Once TLS has been negotiated (i.e. the connection has been secured) it is possible to
+ * register with the server, authenticate using Non-SASL or authenticate using SASL. If the
+ * server supports SASL then Smack will first try to authenticate using SASL. But if that
+ * fails then Non-SASL will be tried.</p>
+ *
+ * <p>The server may support many SASL mechanisms to use for authenticating. Out of the box
+ * Smack provides several SASL mechanisms, but it is possible to register new SASL Mechanisms. Use
+ * {@link #registerSASLMechanism(String, Class)} to register a new mechanisms. A registered
+ * mechanism wont be used until {@link #supportSASLMechanism(String, int)} is called. By default,
+ * the list of supported SASL mechanisms is determined from the {@link SmackConfiguration}. </p>
+ *
+ * <p>Once the user has been authenticated with SASL, it is necessary to bind a resource for
+ * the connection. If no resource is passed in {@link #authenticate(String, String, String)}
+ * then the server will assign a resource for the connection. In case a resource is passed
+ * then the server will receive the desired resource but may assign a modified resource for
+ * the connection.</p>
+ *
+ * <p>Once a resource has been binded and if the server supports sessions then Smack will establish
+ * a session so that instant messaging and presence functionalities may be used.</p>
+ *
+ * @see org.jivesoftware.smack.sasl.SASLMechanism
+ *
+ * @author Gaston Dombiak
+ * @author Jay Kline
+ */
+public class SASLAuthentication implements UserAuthentication {
+
+    private static Map<String, Class<? extends SASLMechanism>> implementedMechanisms = new HashMap<String, Class<? extends SASLMechanism>>();
+    private static List<String> mechanismsPreferences = new ArrayList<String>();
+
+    private Connection connection;
+    private Collection<String> serverMechanisms = new ArrayList<String>();
+    private SASLMechanism currentMechanism = null;
+    /**
+     * Boolean indicating if SASL negotiation has finished and was successful.
+     */
+    private boolean saslNegotiated;
+    /**
+     * Boolean indication if SASL authentication has failed. When failed the server may end
+     * the connection.
+     */
+    private boolean saslFailed;
+    private boolean resourceBinded;
+    private boolean sessionSupported;
+    /**
+     * The SASL related error condition if there was one provided by the server.
+     */
+    private String errorCondition;
+
+    static {
+
+        // Register SASL mechanisms supported by Smack
+        registerSASLMechanism("EXTERNAL", SASLExternalMechanism.class);
+        registerSASLMechanism("GSSAPI", SASLGSSAPIMechanism.class);
+        registerSASLMechanism("DIGEST-MD5", SASLDigestMD5Mechanism.class);
+        registerSASLMechanism("CRAM-MD5", SASLCramMD5Mechanism.class);
+        registerSASLMechanism("PLAIN", SASLPlainMechanism.class);
+        registerSASLMechanism("ANONYMOUS", SASLAnonymous.class);
+
+        supportSASLMechanism("GSSAPI",0);
+        supportSASLMechanism("DIGEST-MD5",1);
+        supportSASLMechanism("CRAM-MD5",2);
+        supportSASLMechanism("PLAIN",3);
+        supportSASLMechanism("ANONYMOUS",4);
+
+    }
+
+    /**
+     * Registers a new SASL mechanism
+     *
+     * @param name   common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     * @param mClass a SASLMechanism subclass.
+     */
+    public static void registerSASLMechanism(String name, Class<? extends SASLMechanism> mClass) {
+        implementedMechanisms.put(name, mClass);
+    }
+
+    /**
+     * Unregisters an existing SASL mechanism. Once the mechanism has been unregistered it won't
+     * be possible to authenticate users using the removed SASL mechanism. It also removes the
+     * mechanism from the supported list.
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void unregisterSASLMechanism(String name) {
+        implementedMechanisms.remove(name);
+        mechanismsPreferences.remove(name);
+    }
+
+
+    /**
+     * Registers a new SASL mechanism in the specified preference position. The client will try
+     * to authenticate using the most prefered SASL mechanism that is also supported by the server.
+     * The SASL mechanism must be registered via {@link #registerSASLMechanism(String, Class)}
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void supportSASLMechanism(String name) {
+        mechanismsPreferences.add(0, name);
+    }
+
+    /**
+     * Registers a new SASL mechanism in the specified preference position. The client will try
+     * to authenticate using the most prefered SASL mechanism that is also supported by the server.
+     * Use the <tt>index</tt> parameter to set the level of preference of the new SASL mechanism.
+     * A value of 0 means that the mechanism is the most prefered one. The SASL mechanism must be
+     * registered via {@link #registerSASLMechanism(String, Class)}
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     * @param index preference position amongst all the implemented SASL mechanism. Starts with 0.
+     */
+    public static void supportSASLMechanism(String name, int index) {
+        mechanismsPreferences.add(index, name);
+    }
+
+    /**
+     * Un-supports an existing SASL mechanism. Once the mechanism has been unregistered it won't
+     * be possible to authenticate users using the removed SASL mechanism. Note that the mechanism
+     * is still registered, but will just not be used.
+     *
+     * @param name common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or KERBEROS_V4.
+     */
+    public static void unsupportSASLMechanism(String name) {
+        mechanismsPreferences.remove(name);
+    }
+
+    /**
+     * Returns the registerd SASLMechanism classes sorted by the level of preference.
+     *
+     * @return the registerd SASLMechanism classes sorted by the level of preference.
+     */
+    public static List<Class<? extends SASLMechanism>> getRegisterSASLMechanisms() {
+        List<Class<? extends SASLMechanism>> answer = new ArrayList<Class<? extends SASLMechanism>>();
+        for (String mechanismsPreference : mechanismsPreferences) {
+            answer.add(implementedMechanisms.get(mechanismsPreference));
+        }
+        return answer;
+    }
+
+    SASLAuthentication(Connection connection) {
+        super();
+        this.connection = connection;
+        this.init();
+    }
+
+    /**
+     * Returns true if the server offered ANONYMOUS SASL as a way to authenticate users.
+     *
+     * @return true if the server offered ANONYMOUS SASL as a way to authenticate users.
+     */
+    public boolean hasAnonymousAuthentication() {
+        return serverMechanisms.contains("ANONYMOUS");
+    }
+
+    /**
+     * Returns true if the server offered SASL authentication besides ANONYMOUS SASL.
+     *
+     * @return true if the server offered SASL authentication besides ANONYMOUS SASL.
+     */
+    public boolean hasNonAnonymousAuthentication() {
+        return !serverMechanisms.isEmpty() && (serverMechanisms.size() != 1 || !hasAnonymousAuthentication());
+    }
+
+    /**
+     * Performs SASL authentication of the specified user. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server may assign a full JID with a username or resource different than the requested
+     * by this method.
+     *
+     * @param username the username that is authenticating with the server.
+     * @param resource the desired resource.
+     * @param cbh the CallbackHandler used to get information from the user
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticate(String username, String resource, CallbackHandler cbh) 
+            throws XMPPException {
+        // Locate the SASLMechanism to use
+        String selectedMechanism = null;
+        for (String mechanism : mechanismsPreferences) {
+            if (implementedMechanisms.containsKey(mechanism) &&
+                    serverMechanisms.contains(mechanism)) {
+                selectedMechanism = mechanism;
+                break;
+            }
+        }
+        if (selectedMechanism != null) {
+            // A SASL mechanism was found. Authenticate using the selected mechanism and then
+            // proceed to bind a resource
+            try {
+                Class<? extends SASLMechanism> mechanismClass = implementedMechanisms.get(selectedMechanism);
+                Constructor<? extends SASLMechanism> constructor = mechanismClass.getConstructor(SASLAuthentication.class);
+                currentMechanism = constructor.newInstance(this);
+                // Trigger SASL authentication with the selected mechanism. We use
+                // connection.getHost() since GSAPI requires the FQDN of the server, which
+                // may not match the XMPP domain.
+                currentMechanism.authenticate(username, connection.getHost(), cbh);
+
+                // Wait until SASL negotiation finishes
+                synchronized (this) {
+                    if (!saslNegotiated && !saslFailed) {
+                        try {
+                            wait(30000);
+                        }
+                        catch (InterruptedException e) {
+                            // Ignore
+                        }
+                    }
+                }
+
+                if (saslFailed) {
+                    // SASL authentication failed and the server may have closed the connection
+                    // so throw an exception
+                    if (errorCondition != null) {
+                        throw new XMPPException("SASL authentication " +
+                                selectedMechanism + " failed: " + errorCondition);
+                    }
+                    else {
+                        throw new XMPPException("SASL authentication failed using mechanism " +
+                                selectedMechanism);
+                    }
+                }
+
+                if (saslNegotiated) {
+                    // Bind a resource for this connection and
+                    return bindResourceAndEstablishSession(resource);
+                } else {
+                    // SASL authentication failed
+                }
+            }
+            catch (XMPPException e) {
+                throw e;
+            }
+            catch (Exception e) {
+                e.printStackTrace();
+            }
+        }
+        else {
+            throw new XMPPException("SASL Authentication failed. No known authentication mechanisims.");
+        }
+        throw new XMPPException("SASL authentication failed");
+    }
+
+    /**
+     * Performs SASL authentication of the specified user. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server may assign a full JID with a username or resource different than the requested
+     * by this method.
+     *
+     * @param username the username that is authenticating with the server.
+     * @param password the password to send to the server.
+     * @param resource the desired resource.
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticate(String username, String password, String resource)
+            throws XMPPException {
+        // Locate the SASLMechanism to use
+        String selectedMechanism = null;
+        for (String mechanism : mechanismsPreferences) {
+            if (implementedMechanisms.containsKey(mechanism) &&
+                    serverMechanisms.contains(mechanism)) {
+                selectedMechanism = mechanism;
+                break;
+            }
+        }
+        if (selectedMechanism != null) {
+            // A SASL mechanism was found. Authenticate using the selected mechanism and then
+            // proceed to bind a resource
+            try {
+                Class<? extends SASLMechanism> mechanismClass = implementedMechanisms.get(selectedMechanism);
+                Constructor<? extends SASLMechanism> constructor = mechanismClass.getConstructor(SASLAuthentication.class);
+                currentMechanism = constructor.newInstance(this);
+                // Trigger SASL authentication with the selected mechanism. We use
+                // connection.getHost() since GSAPI requires the FQDN of the server, which
+                // may not match the XMPP domain.
+                currentMechanism.authenticate(username, connection.getServiceName(), password);
+
+                // Wait until SASL negotiation finishes
+                synchronized (this) {
+                    if (!saslNegotiated && !saslFailed) {
+                        try {
+                            wait(30000);
+                        }
+                        catch (InterruptedException e) {
+                            // Ignore
+                        }
+                    }
+                }
+
+                if (saslFailed) {
+                    // SASL authentication failed and the server may have closed the connection
+                    // so throw an exception
+                    if (errorCondition != null) {
+                        throw new XMPPException("SASL authentication " +
+                                selectedMechanism + " failed: " + errorCondition);
+                    }
+                    else {
+                        throw new XMPPException("SASL authentication failed using mechanism " +
+                                selectedMechanism);
+                    }
+                }
+
+                if (saslNegotiated) {
+                    // Bind a resource for this connection and
+                    return bindResourceAndEstablishSession(resource);
+                }
+                else {
+                    // SASL authentication failed so try a Non-SASL authentication
+                    return new NonSASLAuthentication(connection)
+                            .authenticate(username, password, resource);
+                }
+            }
+            catch (XMPPException e) {
+                throw e;
+            }
+            catch (Exception e) {
+                e.printStackTrace();
+                // SASL authentication failed so try a Non-SASL authentication
+                return new NonSASLAuthentication(connection)
+                        .authenticate(username, password, resource);
+            }
+        }
+        else {
+            // No SASL method was found so try a Non-SASL authentication
+            return new NonSASLAuthentication(connection).authenticate(username, password, resource);
+        }
+    }
+
+    /**
+     * Performs ANONYMOUS SASL authentication. If SASL authentication was successful
+     * then resource binding and session establishment will be performed. This method will return
+     * the full JID provided by the server while binding a resource to the connection.<p>
+     *
+     * The server will assign a full JID with a randomly generated resource and possibly with
+     * no username.
+     *
+     * @return the full JID provided by the server while binding a resource to the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    public String authenticateAnonymously() throws XMPPException {
+        try {
+            currentMechanism = new SASLAnonymous(this);
+            currentMechanism.authenticate(null,null,"");
+
+            // Wait until SASL negotiation finishes
+            synchronized (this) {
+                if (!saslNegotiated && !saslFailed) {
+                    try {
+                        wait(5000);
+                    }
+                    catch (InterruptedException e) {
+                        // Ignore
+                    }
+                }
+            }
+
+            if (saslFailed) {
+                // SASL authentication failed and the server may have closed the connection
+                // so throw an exception
+                if (errorCondition != null) {
+                    throw new XMPPException("SASL authentication failed: " + errorCondition);
+                }
+                else {
+                    throw new XMPPException("SASL authentication failed");
+                }
+            }
+
+            if (saslNegotiated) {
+                // Bind a resource for this connection and
+                return bindResourceAndEstablishSession(null);
+            }
+            else {
+                return new NonSASLAuthentication(connection).authenticateAnonymously();
+            }
+        } catch (IOException e) {
+            return new NonSASLAuthentication(connection).authenticateAnonymously();
+        }
+    }
+
+    private String bindResourceAndEstablishSession(String resource) throws XMPPException {
+        // Wait until server sends response containing the <bind> element
+        synchronized (this) {
+            if (!resourceBinded) {
+                try {
+                    wait(30000);
+                }
+                catch (InterruptedException e) {
+                    // Ignore
+                }
+            }
+        }
+
+        if (!resourceBinded) {
+            // Server never offered resource binding
+            throw new XMPPException("Resource binding not offered by server");
+        }
+
+        Bind bindResource = new Bind();
+        bindResource.setResource(resource);
+
+        PacketCollector collector = connection
+                .createPacketCollector(new PacketIDFilter(bindResource.getPacketID()));
+        // Send the packet
+        connection.sendPacket(bindResource);
+        // Wait up to a certain number of seconds for a response from the server.
+        Bind response = (Bind) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        String userJID = response.getJid();
+
+        if (sessionSupported) {
+            Session session = new Session();
+            collector = connection.createPacketCollector(new PacketIDFilter(session.getPacketID()));
+            // Send the packet
+            connection.sendPacket(session);
+            // Wait up to a certain number of seconds for a response from the server.
+            IQ ack = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+            collector.cancel();
+            if (ack == null) {
+                throw new XMPPException("No response from the server.");
+            }
+            // If the server replied with an error, throw an exception.
+            else if (ack.getType() == IQ.Type.ERROR) {
+                throw new XMPPException(ack.getError());
+            }
+        }
+        return userJID;
+    }
+
+    /**
+     * Sets the available SASL mechanism reported by the server. The server will report the
+     * available SASL mechanism once the TLS negotiation was successful. This information is
+     * stored and will be used when doing the authentication for logging in the user.
+     *
+     * @param mechanisms collection of strings with the available SASL mechanism reported
+     *                   by the server.
+     */
+    void setAvailableSASLMethods(Collection<String> mechanisms) {
+        this.serverMechanisms = mechanisms;
+    }
+
+    /**
+     * Returns true if the user was able to authenticate with the server usins SASL.
+     *
+     * @return true if the user was able to authenticate with the server usins SASL.
+     */
+    public boolean isAuthenticated() {
+        return saslNegotiated;
+    }
+
+    /**
+     * The server is challenging the SASL authentication we just sent. Forward the challenge
+     * to the current SASLMechanism we are using. The SASLMechanism will send a response to
+     * the server. The length of the challenge-response sequence varies according to the
+     * SASLMechanism in use.
+     *
+     * @param challenge a base64 encoded string representing the challenge.
+     * @throws IOException If a network error occures while authenticating.
+     */
+    void challengeReceived(String challenge) throws IOException {
+        currentMechanism.challengeReceived(challenge);
+    }
+
+    /**
+     * Notification message saying that SASL authentication was successful. The next step
+     * would be to bind the resource.
+     */
+    void authenticated() {
+        synchronized (this) {
+            saslNegotiated = true;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    /**
+     * Notification message saying that SASL authentication has failed. The server may have
+     * closed the connection depending on the number of possible retries.
+     * 
+     * @deprecated replaced by {@see #authenticationFailed(String)}.
+     */
+    void authenticationFailed() {
+        authenticationFailed(null);
+    }
+
+    /**
+     * Notification message saying that SASL authentication has failed. The server may have
+     * closed the connection depending on the number of possible retries.
+     * 
+     * @param condition the error condition provided by the server.
+     */
+    void authenticationFailed(String condition) {
+        synchronized (this) {
+            saslFailed = true;
+            errorCondition = condition;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    /**
+     * Notification message saying that the server requires the client to bind a
+     * resource to the stream.
+     */
+    void bindingRequired() {
+        synchronized (this) {
+            resourceBinded = true;
+            // Wake up the thread that is waiting in the #authenticate method
+            notify();
+        }
+    }
+
+    public void send(Packet stanza) {
+        connection.sendPacket(stanza);
+    }
+
+    /**
+     * Notification message saying that the server supports sessions. When a server supports
+     * sessions the client needs to send a Session packet after successfully binding a resource
+     * for the session.
+     */
+    void sessionsSupported() {
+        sessionSupported = true;
+    }
+    
+    /**
+     * Initializes the internal state in order to be able to be reused. The authentication
+     * is used by the connection at the first login and then reused after the connection
+     * is disconnected and then reconnected.
+     */
+    protected void init() {
+        saslNegotiated = false;
+        saslFailed = false;
+        resourceBinded = false;
+        sessionSupported = false;
+    }
+}
diff --git a/src/org/jivesoftware/smack/ServerTrustManager.java b/src/org/jivesoftware/smack/ServerTrustManager.java
new file mode 100644
index 0000000..63da3e7
--- /dev/null
+++ b/src/org/jivesoftware/smack/ServerTrustManager.java
@@ -0,0 +1,331 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import javax.net.ssl.X509TrustManager;
+
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.io.IOException;
+import java.security.*;
+import java.security.cert.CertificateException;
+import java.security.cert.CertificateParsingException;
+import java.security.cert.X509Certificate;
+import java.util.*;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Trust manager that checks all certificates presented by the server. This class
+ * is used during TLS negotiation. It is possible to disable/enable some or all checkings
+ * by configuring the {@link ConnectionConfiguration}. The truststore file that contains
+ * knows and trusted CA root certificates can also be configure in {@link ConnectionConfiguration}.
+ *
+ * @author Gaston Dombiak
+ */
+class ServerTrustManager implements X509TrustManager {
+
+    private static Pattern cnPattern = Pattern.compile("(?i)(cn=)([^,]*)");
+
+    private ConnectionConfiguration configuration;
+
+    /**
+     * Holds the domain of the remote server we are trying to connect
+     */
+    private String server;
+    private KeyStore trustStore;
+    
+    private static Map<KeyStoreOptions, KeyStore> stores = new HashMap<KeyStoreOptions, KeyStore>();
+
+    public ServerTrustManager(String server, ConnectionConfiguration configuration) {
+        this.configuration = configuration;
+        this.server = server;
+
+        InputStream in = null;
+        synchronized (stores) {
+            KeyStoreOptions options = new KeyStoreOptions(configuration.getTruststoreType(),
+                    configuration.getTruststorePath(), configuration.getTruststorePassword());
+            if (stores.containsKey(options)) {
+                trustStore = stores.get(options);
+            } else {
+                try {
+                    trustStore = KeyStore.getInstance(options.getType());
+                    in = new FileInputStream(options.getPath());
+                    trustStore.load(in, options.getPassword().toCharArray());
+                } catch (Exception e) {
+                    trustStore = null;
+                    e.printStackTrace();
+                } finally {
+                    if (in != null) {
+                        try {
+                            in.close();
+                        } catch (IOException ioe) {
+                            // Ignore.
+                        }
+                    }
+                }
+                stores.put(options, trustStore);
+            }
+            if (trustStore == null)
+                // Disable root CA checking
+                configuration.setVerifyRootCAEnabled(false);
+        }
+    }
+
+    public X509Certificate[] getAcceptedIssuers() {
+        return new X509Certificate[0];
+    }
+
+    public void checkClientTrusted(X509Certificate[] arg0, String arg1)
+            throws CertificateException {
+    }
+
+    public void checkServerTrusted(X509Certificate[] x509Certificates, String arg1)
+            throws CertificateException {
+
+        int nSize = x509Certificates.length;
+
+        List<String> peerIdentities = getPeerIdentity(x509Certificates[0]);
+
+        if (configuration.isVerifyChainEnabled()) {
+            // Working down the chain, for every certificate in the chain,
+            // verify that the subject of the certificate is the issuer of the
+            // next certificate in the chain.
+            Principal principalLast = null;
+            for (int i = nSize -1; i >= 0 ; i--) {
+                X509Certificate x509certificate = x509Certificates[i];
+                Principal principalIssuer = x509certificate.getIssuerDN();
+                Principal principalSubject = x509certificate.getSubjectDN();
+                if (principalLast != null) {
+                    if (principalIssuer.equals(principalLast)) {
+                        try {
+                            PublicKey publickey =
+                                    x509Certificates[i + 1].getPublicKey();
+                            x509Certificates[i].verify(publickey);
+                        }
+                        catch (GeneralSecurityException generalsecurityexception) {
+                            throw new CertificateException(
+                                    "signature verification failed of " + peerIdentities);
+                        }
+                    }
+                    else {
+                        throw new CertificateException(
+                                "subject/issuer verification failed of " + peerIdentities);
+                    }
+                }
+                principalLast = principalSubject;
+            }
+        }
+
+        if (configuration.isVerifyRootCAEnabled()) {
+            // Verify that the the last certificate in the chain was issued
+            // by a third-party that the client trusts.
+            boolean trusted = false;
+            try {
+                trusted = trustStore.getCertificateAlias(x509Certificates[nSize - 1]) != null;
+                if (!trusted && nSize == 1 && configuration.isSelfSignedCertificateEnabled())
+                {
+                    System.out.println("Accepting self-signed certificate of remote server: " +
+                            peerIdentities);
+                    trusted = true;
+                }
+            }
+            catch (KeyStoreException e) {
+                e.printStackTrace();
+            }
+            if (!trusted) {
+                throw new CertificateException("root certificate not trusted of " + peerIdentities);
+            }
+        }
+
+        if (configuration.isNotMatchingDomainCheckEnabled()) {
+            // Verify that the first certificate in the chain corresponds to
+            // the server we desire to authenticate.
+            // Check if the certificate uses a wildcard indicating that subdomains are valid
+            if (peerIdentities.size() == 1 && peerIdentities.get(0).startsWith("*.")) {
+                // Remove the wildcard
+                String peerIdentity = peerIdentities.get(0).replace("*.", "");
+                // Check if the requested subdomain matches the certified domain
+                if (!server.endsWith(peerIdentity)) {
+                    throw new CertificateException("target verification failed of " + peerIdentities);
+                }
+            }
+            else if (!peerIdentities.contains(server)) {
+                throw new CertificateException("target verification failed of " + peerIdentities);
+            }
+        }
+
+        if (configuration.isExpiredCertificatesCheckEnabled()) {
+            // For every certificate in the chain, verify that the certificate
+            // is valid at the current time.
+            Date date = new Date();
+            for (int i = 0; i < nSize; i++) {
+                try {
+                    x509Certificates[i].checkValidity(date);
+                }
+                catch (GeneralSecurityException generalsecurityexception) {
+                    throw new CertificateException("invalid date of " + server);
+                }
+            }
+        }
+
+    }
+
+    /**
+     * Returns the identity of the remote server as defined in the specified certificate. The
+     * identity is defined in the subjectDN of the certificate and it can also be defined in
+     * the subjectAltName extension of type "xmpp". When the extension is being used then the
+     * identity defined in the extension in going to be returned. Otherwise, the value stored in
+     * the subjectDN is returned.
+     *
+     * @param x509Certificate the certificate the holds the identity of the remote server.
+     * @return the identity of the remote server as defined in the specified certificate.
+     */
+    public static List<String> getPeerIdentity(X509Certificate x509Certificate) {
+        // Look the identity in the subjectAltName extension if available
+        List<String> names = getSubjectAlternativeNames(x509Certificate);
+        if (names.isEmpty()) {
+            String name = x509Certificate.getSubjectDN().getName();
+            Matcher matcher = cnPattern.matcher(name);
+            if (matcher.find()) {
+                name = matcher.group(2);
+            }
+            // Create an array with the unique identity
+            names = new ArrayList<String>();
+            names.add(name);
+        }
+        return names;
+    }
+
+    /**
+     * Returns the JID representation of an XMPP entity contained as a SubjectAltName extension
+     * in the certificate. If none was found then return <tt>null</tt>.
+     *
+     * @param certificate the certificate presented by the remote entity.
+     * @return the JID representation of an XMPP entity contained as a SubjectAltName extension
+     *         in the certificate. If none was found then return <tt>null</tt>.
+     */
+    private static List<String> getSubjectAlternativeNames(X509Certificate certificate) {
+        List<String> identities = new ArrayList<String>();
+        try {
+            Collection<List<?>> altNames = certificate.getSubjectAlternativeNames();
+            // Check that the certificate includes the SubjectAltName extension
+            if (altNames == null) {
+                return Collections.emptyList();
+            }
+            // Use the type OtherName to search for the certified server name
+            /*for (List item : altNames) {
+                Integer type = (Integer) item.get(0);
+                if (type == 0) {
+                    // Type OtherName found so return the associated value
+                    try {
+                        // Value is encoded using ASN.1 so decode it to get the server's identity
+                        ASN1InputStream decoder = new ASN1InputStream((byte[]) item.toArray()[1]);
+                        DEREncodable encoded = decoder.readObject();
+                        encoded = ((DERSequence) encoded).getObjectAt(1);
+                        encoded = ((DERTaggedObject) encoded).getObject();
+                        encoded = ((DERTaggedObject) encoded).getObject();
+                        String identity = ((DERUTF8String) encoded).getString();
+                        // Add the decoded server name to the list of identities
+                        identities.add(identity);
+                    }
+                    catch (UnsupportedEncodingException e) {
+                        // Ignore
+                    }
+                    catch (IOException e) {
+                        // Ignore
+                    }
+                    catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                }
+                // Other types are not good for XMPP so ignore them
+                System.out.println("SubjectAltName of invalid type found: " + certificate);
+            }*/
+        }
+        catch (CertificateParsingException e) {
+            e.printStackTrace();
+        }
+        return identities;
+    }
+
+    private static class KeyStoreOptions {
+        private final String type;
+        private final String path;
+        private final String password;
+
+        public KeyStoreOptions(String type, String path, String password) {
+            super();
+            this.type = type;
+            this.path = path;
+            this.password = password;
+        }
+
+        public String getType() {
+            return type;
+        }
+
+        public String getPath() {
+            return path;
+        }
+
+        public String getPassword() {
+            return password;
+        }
+
+        @Override
+        public int hashCode() {
+            final int prime = 31;
+            int result = 1;
+            result = prime * result + ((password == null) ? 0 : password.hashCode());
+            result = prime * result + ((path == null) ? 0 : path.hashCode());
+            result = prime * result + ((type == null) ? 0 : type.hashCode());
+            return result;
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (this == obj)
+                return true;
+            if (obj == null)
+                return false;
+            if (getClass() != obj.getClass())
+                return false;
+            KeyStoreOptions other = (KeyStoreOptions) obj;
+            if (password == null) {
+                if (other.password != null)
+                    return false;
+            } else if (!password.equals(other.password))
+                return false;
+            if (path == null) {
+                if (other.path != null)
+                    return false;
+            } else if (!path.equals(other.path))
+                return false;
+            if (type == null) {
+                if (other.type != null)
+                    return false;
+            } else if (!type.equals(other.type))
+                return false;
+            return true;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/SmackAndroid.java b/src/org/jivesoftware/smack/SmackAndroid.java
new file mode 100644
index 0000000..a18d675
--- /dev/null
+++ b/src/org/jivesoftware/smack/SmackAndroid.java
@@ -0,0 +1,59 @@
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.util.DNSUtil;
+import org.jivesoftware.smack.util.dns.DNSJavaResolver;
+import org.jivesoftware.smackx.ConfigureProviderManager;
+import org.jivesoftware.smackx.InitStaticCode;
+import org.xbill.DNS.ResolverConfig;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+
+public class SmackAndroid {
+    private static SmackAndroid sSmackAndroid = null;
+
+    private BroadcastReceiver mConnectivityChangedReceiver;
+    private Context mCtx;
+
+    private SmackAndroid(Context ctx) {
+        mCtx = ctx;
+        DNSUtil.setDNSResolver(DNSJavaResolver.getInstance());
+        InitStaticCode.initStaticCode(ctx);
+        ConfigureProviderManager.configureProviderManager();
+        maybeRegisterReceiver();
+    }
+
+    public static SmackAndroid init(Context ctx) {
+        if (sSmackAndroid == null) {
+            sSmackAndroid = new SmackAndroid(ctx);
+        } else {
+            sSmackAndroid.maybeRegisterReceiver();
+        }
+        return sSmackAndroid;
+    }
+
+    public void onDestroy() {
+        if (mConnectivityChangedReceiver != null) {
+            mCtx.unregisterReceiver(mConnectivityChangedReceiver);
+            mConnectivityChangedReceiver = null;
+        }
+    }
+
+    private void maybeRegisterReceiver() {
+        if (mConnectivityChangedReceiver == null) {
+            mConnectivityChangedReceiver = new ConnectivtyChangedReceiver();
+            mCtx.registerReceiver(mConnectivityChangedReceiver, new IntentFilter("android.net.conn.CONNECTIVITY_CHANGE"));
+        }
+    }
+
+    class ConnectivtyChangedReceiver extends BroadcastReceiver {
+
+        @Override
+        public void onReceive(Context context, Intent intent) {
+            ResolverConfig.refresh();
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smack/SmackConfiguration.java b/src/org/jivesoftware/smack/SmackConfiguration.java
new file mode 100644
index 0000000..2696d87
--- /dev/null
+++ b/src/org/jivesoftware/smack/SmackConfiguration.java
@@ -0,0 +1,371 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import java.io.InputStream;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Enumeration;
+import java.util.List;
+import java.util.Vector;
+
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Represents the configuration of Smack. The configuration is used for:
+ * <ul>
+ *      <li> Initializing classes by loading them at start-up.
+ *      <li> Getting the current Smack version.
+ *      <li> Getting and setting global library behavior, such as the period of time
+ *          to wait for replies to packets from the server. Note: setting these values
+ *          via the API will override settings in the configuration file.
+ * </ul>
+ *
+ * Configuration settings are stored in META-INF/smack-config.xml (typically inside the
+ * smack.jar file).
+ * 
+ * @author Gaston Dombiak
+ */
+public final class SmackConfiguration {
+
+    private static final String SMACK_VERSION = "3.2.2";
+
+    private static int packetReplyTimeout = 5000;
+    private static Vector<String> defaultMechs = new Vector<String>();
+
+    private static boolean localSocks5ProxyEnabled = true;
+    private static int localSocks5ProxyPort = 7777;
+    private static int packetCollectorSize = 5000;
+
+    /**
+     * defaultPingInterval (in seconds)
+     */
+    private static int defaultPingInterval = 1800; // 30 min (30*60)
+
+    /**
+     * This automatically enables EntityCaps for new connections if it is set to true
+     */
+    private static boolean autoEnableEntityCaps = false;
+
+    private SmackConfiguration() {
+    }
+
+    /**
+     * Loads the configuration from the smack-config.xml file.<p>
+     * 
+     * So far this means that:
+     * 1) a set of classes will be loaded in order to execute their static init block
+     * 2) retrieve and set the current Smack release
+     */
+    static {
+        try {
+            // Get an array of class loaders to try loading the providers files from.
+            ClassLoader[] classLoaders = getClassLoaders();
+            for (ClassLoader classLoader : classLoaders) {
+                Enumeration<URL> configEnum = classLoader.getResources("META-INF/smack-config.xml");
+                while (configEnum.hasMoreElements()) {
+                    URL url = configEnum.nextElement();
+                    InputStream systemStream = null;
+                    try {
+                        systemStream = url.openStream();
+                        XmlPullParser parser = XmlPullParserFactory.newInstance().newPullParser();
+                        parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+                        parser.setInput(systemStream, "UTF-8");
+                        int eventType = parser.getEventType();
+                        do {
+                            if (eventType == XmlPullParser.START_TAG) {
+                                if (parser.getName().equals("className")) {
+                                    // Attempt to load the class so that the class can get initialized
+                                    parseClassToLoad(parser);
+                                }
+                                else if (parser.getName().equals("packetReplyTimeout")) {
+                                    packetReplyTimeout = parseIntProperty(parser, packetReplyTimeout);
+                                }
+                                else if (parser.getName().equals("mechName")) {
+                                    defaultMechs.add(parser.nextText());
+                                } 
+                                else if (parser.getName().equals("localSocks5ProxyEnabled")) {
+                                    localSocks5ProxyEnabled = Boolean.parseBoolean(parser.nextText());
+                                } 
+                                else if (parser.getName().equals("localSocks5ProxyPort")) {
+                                    localSocks5ProxyPort = parseIntProperty(parser, localSocks5ProxyPort);
+                                }
+                                else if (parser.getName().equals("packetCollectorSize")) {
+                                    packetCollectorSize = parseIntProperty(parser, packetCollectorSize);
+                                }
+                                else if (parser.getName().equals("defaultPingInterval")) {
+                                    defaultPingInterval = parseIntProperty(parser, defaultPingInterval);
+                                }
+                                else if (parser.getName().equals("autoEnableEntityCaps")) {
+                                    autoEnableEntityCaps = Boolean.parseBoolean(parser.nextText());
+                                }
+                            }
+                            eventType = parser.next();
+                        }
+                        while (eventType != XmlPullParser.END_DOCUMENT);
+                    }
+                    catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                    finally {
+                        try {
+                            systemStream.close();
+                        }
+                        catch (Exception e) {
+                            // Ignore.
+                        }
+                    }
+                }
+            }
+        }
+        catch (Exception e) {
+            e.printStackTrace();
+        }
+    }
+
+    /**
+     * Returns the Smack version information, eg "1.3.0".
+     * 
+     * @return the Smack version information.
+     */
+    public static String getVersion() {
+        return SMACK_VERSION;
+    }
+
+    /**
+     * Returns the number of milliseconds to wait for a response from
+     * the server. The default value is 5000 ms.
+     * 
+     * @return the milliseconds to wait for a response from the server
+     */
+    public static int getPacketReplyTimeout() {
+        // The timeout value must be greater than 0 otherwise we will answer the default value
+        if (packetReplyTimeout <= 0) {
+            packetReplyTimeout = 5000;
+        }
+        return packetReplyTimeout;
+    }
+
+    /**
+     * Sets the number of milliseconds to wait for a response from
+     * the server.
+     * 
+     * @param timeout the milliseconds to wait for a response from the server
+     */
+    public static void setPacketReplyTimeout(int timeout) {
+        if (timeout <= 0) {
+            throw new IllegalArgumentException();
+        }
+        packetReplyTimeout = timeout;
+    }
+
+    /**
+     * Gets the default max size of a packet collector before it will delete 
+     * the older packets.
+     * 
+     * @return The number of packets to queue before deleting older packets.
+     */
+    public static int getPacketCollectorSize() {
+    	return packetCollectorSize;
+    }
+
+    /**
+     * Sets the default max size of a packet collector before it will delete 
+     * the older packets.
+     * 
+     * @param The number of packets to queue before deleting older packets.
+     */
+    public static void setPacketCollectorSize(int collectorSize) {
+    	packetCollectorSize = collectorSize;
+    }
+    
+    /**
+     * Add a SASL mechanism to the list to be used.
+     *
+     * @param mech the SASL mechanism to be added
+     */
+    public static void addSaslMech(String mech) {
+        if(! defaultMechs.contains(mech) ) {
+            defaultMechs.add(mech);
+        }
+    }
+
+   /**
+     * Add a Collection of SASL mechanisms to the list to be used.
+     *
+     * @param mechs the Collection of SASL mechanisms to be added
+     */
+    public static void addSaslMechs(Collection<String> mechs) {
+        for(String mech : mechs) {
+            addSaslMech(mech);
+        }
+    }
+
+    /**
+     * Remove a SASL mechanism from the list to be used.
+     *
+     * @param mech the SASL mechanism to be removed
+     */
+    public static void removeSaslMech(String mech) {
+        if( defaultMechs.contains(mech) ) {
+            defaultMechs.remove(mech);
+        }
+    }
+
+   /**
+     * Remove a Collection of SASL mechanisms to the list to be used.
+     *
+     * @param mechs the Collection of SASL mechanisms to be removed
+     */
+    public static void removeSaslMechs(Collection<String> mechs) {
+        for(String mech : mechs) {
+            removeSaslMech(mech);
+        }
+    }
+
+    /**
+     * Returns the list of SASL mechanisms to be used. If a SASL mechanism is
+     * listed here it does not guarantee it will be used. The server may not
+     * support it, or it may not be implemented.
+     *
+     * @return the list of SASL mechanisms to be used.
+     */
+    public static List<String> getSaslMechs() {
+        return defaultMechs;
+    }
+
+    /**
+     * Returns true if the local Socks5 proxy should be started. Default is true.
+     * 
+     * @return if the local Socks5 proxy should be started
+     */
+    public static boolean isLocalSocks5ProxyEnabled() {
+        return localSocks5ProxyEnabled;
+    }
+
+    /**
+     * Sets if the local Socks5 proxy should be started. Default is true.
+     * 
+     * @param localSocks5ProxyEnabled if the local Socks5 proxy should be started
+     */
+    public static void setLocalSocks5ProxyEnabled(boolean localSocks5ProxyEnabled) {
+        SmackConfiguration.localSocks5ProxyEnabled = localSocks5ProxyEnabled;
+    }
+
+    /**
+     * Return the port of the local Socks5 proxy. Default is 7777.
+     * 
+     * @return the port of the local Socks5 proxy
+     */
+    public static int getLocalSocks5ProxyPort() {
+        return localSocks5ProxyPort;
+    }
+
+    /**
+     * Sets the port of the local Socks5 proxy. Default is 7777. If you set the port to a negative
+     * value Smack tries the absolute value and all following until it finds an open port.
+     * 
+     * @param localSocks5ProxyPort the port of the local Socks5 proxy to set
+     */
+    public static void setLocalSocks5ProxyPort(int localSocks5ProxyPort) {
+        SmackConfiguration.localSocks5ProxyPort = localSocks5ProxyPort;
+    }
+
+    /**
+     * Returns the default ping interval (seconds)
+     * 
+     * @return
+     */
+    public static int getDefaultPingInterval() {
+        return defaultPingInterval;
+    }
+
+    /**
+     * Sets the default ping interval (seconds). Set it to '-1' to disable the periodic ping
+     *
+     * @param defaultPingInterval
+     */
+    public static void setDefaultPingInterval(int defaultPingInterval) {
+        SmackConfiguration.defaultPingInterval = defaultPingInterval;
+    }
+
+    /**
+     * Check if Entity Caps are enabled as default for every new connection
+     * @return
+     */
+    public static boolean autoEnableEntityCaps() {
+        return autoEnableEntityCaps;
+    }
+
+    /**
+     * Set if Entity Caps are enabled or disabled for every new connection
+     * 
+     * @param true if Entity Caps should be auto enabled, false if not
+     */
+    public static void setAutoEnableEntityCaps(boolean b) {
+        autoEnableEntityCaps = b;
+    }
+
+    private static void parseClassToLoad(XmlPullParser parser) throws Exception {
+        String className = parser.nextText();
+        // Attempt to load the class so that the class can get initialized
+        try {
+            Class.forName(className);
+        }
+        catch (ClassNotFoundException cnfe) {
+            System.err.println("Error! A startup class specified in smack-config.xml could " +
+                    "not be loaded: " + className);
+        }
+    }
+
+    private static int parseIntProperty(XmlPullParser parser, int defaultValue)
+            throws Exception
+    {
+        try {
+            return Integer.parseInt(parser.nextText());
+        }
+        catch (NumberFormatException nfe) {
+            nfe.printStackTrace();
+            return defaultValue;
+        }
+    }
+
+    /**
+     * Returns an array of class loaders to load resources from.
+     *
+     * @return an array of ClassLoader instances.
+     */
+    private static ClassLoader[] getClassLoaders() {
+        ClassLoader[] classLoaders = new ClassLoader[2];
+        classLoaders[0] = SmackConfiguration.class.getClassLoader();
+        classLoaders[1] = Thread.currentThread().getContextClassLoader();
+        // Clean up possible null values. Note that #getClassLoader may return a null value.
+        List<ClassLoader> loaders = new ArrayList<ClassLoader>();
+        for (ClassLoader classLoader : classLoaders) {
+            if (classLoader != null) {
+                loaders.add(classLoader);
+            }
+        }
+        return loaders.toArray(new ClassLoader[loaders.size()]);
+    }
+}
diff --git a/src/org/jivesoftware/smack/UserAuthentication.java b/src/org/jivesoftware/smack/UserAuthentication.java
new file mode 100644
index 0000000..38b30ca
--- /dev/null
+++ b/src/org/jivesoftware/smack/UserAuthentication.java
@@ -0,0 +1,79 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+/**
+ * There are two ways to authenticate a user with a server. Using SASL or Non-SASL
+ * authentication. This interface makes {@link SASLAuthentication} and
+ * {@link NonSASLAuthentication} polyphormic.
+ *
+ * @author Gaston Dombiak
+ * @author Jay Kline
+ */
+interface UserAuthentication {
+
+    /**
+     * Authenticates the user with the server.  This method will return the full JID provided by
+     * the server.  The server may assign a full JID with a username and resource different than
+     * requested by this method.
+     *
+     * Note that using callbacks is the prefered method of authenticating users since it allows
+     * more flexability in the mechanisms used.
+     *
+     * @param username the requested username (authorization ID) for authenticating to the server
+     * @param resource the requested resource.
+     * @param cbh the CallbackHandler used to obtain authentication ID, password, or other
+     * information
+     * @return the full JID provided by the server while binding a resource for the connection.
+     * @throws XMPPException if an error occurs while authenticating.
+     */
+    String authenticate(String username, String resource, CallbackHandler cbh) throws
+            XMPPException;
+
+    /**
+     * Authenticates the user with the server. This method will return the full JID provided by
+     * the server. The server may assign a full JID with a username and resource different than
+     * the requested by this method.
+     *
+     * It is recommended that @{link #authenticate(String, String, CallbackHandler)} be used instead
+     * since it provides greater flexability in authenticaiton and authorization.
+     *
+     * @param username the username that is authenticating with the server.
+     * @param password the password to send to the server.
+     * @param resource the desired resource.
+     * @return the full JID provided by the server while binding a resource for the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    String authenticate(String username, String password, String resource) throws
+            XMPPException;
+
+    /**
+     * Performs an anonymous authentication with the server. The server will created a new full JID
+     * for this connection. An exception will be thrown if the server does not support anonymous
+     * authentication.
+     *
+     * @return the full JID provided by the server while binding a resource for the connection.
+     * @throws XMPPException if an error occures while authenticating.
+     */
+    String authenticateAnonymously() throws XMPPException;
+}
diff --git a/src/org/jivesoftware/smack/XMPPConnection.java b/src/org/jivesoftware/smack/XMPPConnection.java
new file mode 100644
index 0000000..badf29c
--- /dev/null
+++ b/src/org/jivesoftware/smack/XMPPConnection.java
@@ -0,0 +1,1116 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.compression.XMPPInputOutputStream;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smack.util.dns.HostAddress;
+
+import javax.net.ssl.KeyManager;
+import javax.net.ssl.KeyManagerFactory;
+import javax.net.ssl.SSLContext;
+import javax.net.ssl.SSLSocket;
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.ByteArrayInputStream;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.OutputStream;
+import java.io.OutputStreamWriter;
+import java.lang.reflect.Constructor;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import java.security.KeyStore;
+import java.security.Provider;
+import java.security.Security;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+
+/**
+ * Creates a socket connection to a XMPP server. This is the default connection
+ * to a Jabber server and is specified in the XMPP Core (RFC 3920).
+ * 
+ * @see Connection
+ * @author Matt Tucker
+ */
+public class XMPPConnection extends Connection {
+
+    /**
+     * The socket which is used for this connection.
+     */
+    Socket socket;
+
+    String connectionID = null;
+    private String user = null;
+    private boolean connected = false;
+    // socketClosed is used concurrent
+    // by XMPPConnection, PacketReader, PacketWriter
+    private volatile boolean socketClosed = false;
+
+    /**
+     * Flag that indicates if the user is currently authenticated with the server.
+     */
+    private boolean authenticated = false;
+    /**
+     * Flag that indicates if the user was authenticated with the server when the connection
+     * to the server was closed (abruptly or not).
+     */
+    private boolean wasAuthenticated = false;
+    private boolean anonymous = false;
+    private boolean usingTLS = false;
+
+    PacketWriter packetWriter;
+    PacketReader packetReader;
+
+    Roster roster = null;
+
+    /**
+     * Collection of available stream compression methods offered by the server.
+     */
+    private Collection<String> compressionMethods;
+
+    /**
+     * Set to true by packet writer if the server acknowledged the compression
+     */
+    private boolean serverAckdCompression = false;
+
+    /**
+     * Creates a new connection to the specified XMPP server. A DNS SRV lookup will be
+     * performed to determine the IP address and port corresponding to the
+     * service name; if that lookup fails, it's assumed that server resides at
+     * <tt>serviceName</tt> with the default port of 5222. Encrypted connections (TLS)
+     * will be used if available, stream compression is disabled, and standard SASL
+     * mechanisms will be used for authentication.<p>
+     * <p/>
+     * This is the simplest constructor for connecting to an XMPP server. Alternatively,
+     * you can get fine-grained control over connection settings using the
+     * {@link #XMPPConnection(ConnectionConfiguration)} constructor.<p>
+     * <p/>
+     * Note that XMPPConnection constructors do not establish a connection to the server
+     * and you must call {@link #connect()}.<p>
+     * <p/>
+     * The CallbackHandler will only be used if the connection requires the client provide
+     * an SSL certificate to the server. The CallbackHandler must handle the PasswordCallback
+     * to prompt for a password to unlock the keystore containing the SSL certificate.
+     *
+     * @param serviceName the name of the XMPP server to connect to; e.g. <tt>example.com</tt>.
+     * @param callbackHandler the CallbackHandler used to prompt for the password to the keystore.
+     */
+    public XMPPConnection(String serviceName, CallbackHandler callbackHandler) {
+        // Create the configuration for this new connection
+        super(new ConnectionConfiguration(serviceName));
+        config.setCompressionEnabled(false);
+        config.setSASLAuthenticationEnabled(true);
+        config.setDebuggerEnabled(DEBUG_ENABLED);
+        config.setCallbackHandler(callbackHandler);
+    }
+
+    /**
+     * Creates a new XMPP connection in the same way {@link #XMPPConnection(String,CallbackHandler)} does, but
+     * with no callback handler for password prompting of the keystore.  This will work
+     * in most cases, provided the client is not required to provide a certificate to 
+     * the server.
+     *
+     * @param serviceName the name of the XMPP server to connect to; e.g. <tt>example.com</tt>.
+     */
+    public XMPPConnection(String serviceName) {
+        // Create the configuration for this new connection
+        super(new ConnectionConfiguration(serviceName));
+        config.setCompressionEnabled(false);
+        config.setSASLAuthenticationEnabled(true);
+        config.setDebuggerEnabled(DEBUG_ENABLED);
+    }
+
+    /**
+     * Creates a new XMPP connection in the same way {@link #XMPPConnection(ConnectionConfiguration,CallbackHandler)} does, but
+     * with no callback handler for password prompting of the keystore.  This will work
+     * in most cases, provided the client is not required to provide a certificate to 
+     * the server.
+     *
+     *
+     * @param config the connection configuration.
+     */
+    public XMPPConnection(ConnectionConfiguration config) {
+        super(config);
+    }
+
+    /**
+     * Creates a new XMPP connection using the specified connection configuration.<p>
+     * <p/>
+     * Manually specifying connection configuration information is suitable for
+     * advanced users of the API. In many cases, using the
+     * {@link #XMPPConnection(String)} constructor is a better approach.<p>
+     * <p/>
+     * Note that XMPPConnection constructors do not establish a connection to the server
+     * and you must call {@link #connect()}.<p>
+     * <p/>
+     *
+     * The CallbackHandler will only be used if the connection requires the client provide
+     * an SSL certificate to the server. The CallbackHandler must handle the PasswordCallback
+     * to prompt for a password to unlock the keystore containing the SSL certificate.
+     *
+     * @param config the connection configuration.
+     * @param callbackHandler the CallbackHandler used to prompt for the password to the keystore.
+     */
+    public XMPPConnection(ConnectionConfiguration config, CallbackHandler callbackHandler) {
+        super(config);
+        config.setCallbackHandler(callbackHandler);
+    }
+
+    public String getConnectionID() {
+        if (!isConnected()) {
+            return null;
+        }
+        return connectionID;
+    }
+
+    public String getUser() {
+        if (!isAuthenticated()) {
+            return null;
+        }
+        return user;
+    }
+
+    @Override
+    public synchronized void login(String username, String password, String resource) throws XMPPException {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (authenticated) {
+            throw new IllegalStateException("Already logged in to server.");
+        }
+        // Do partial version of nameprep on the username.
+        username = username.toLowerCase().trim();
+
+        String response;
+        if (config.isSASLAuthenticationEnabled() &&
+                saslAuthentication.hasNonAnonymousAuthentication()) {
+            // Authenticate using SASL
+            if (password != null) {
+                response = saslAuthentication.authenticate(username, password, resource);
+            }
+            else {
+                response = saslAuthentication
+                        .authenticate(username, resource, config.getCallbackHandler());
+            }
+        }
+        else {
+            // Authenticate using Non-SASL
+            response = new NonSASLAuthentication(this).authenticate(username, password, resource);
+        }
+
+        // Set the user.
+        if (response != null) {
+            this.user = response;
+            // Update the serviceName with the one returned by the server
+            config.setServiceName(StringUtils.parseServer(response));
+        }
+        else {
+            this.user = username + "@" + getServiceName();
+            if (resource != null) {
+                this.user += "/" + resource;
+            }
+        }
+
+        // If compression is enabled then request the server to use stream compression
+        if (config.isCompressionEnabled()) {
+            useCompression();
+        }
+
+        // Indicate that we're now authenticated.
+        authenticated = true;
+        anonymous = false;
+
+        // Create the roster if it is not a reconnection or roster already created by getRoster()
+        if (this.roster == null) {
+        	if(rosterStorage==null){
+        		this.roster = new Roster(this);
+        	}
+        	else{
+        		this.roster = new Roster(this,rosterStorage);
+        	}
+        }
+        if (config.isRosterLoadedAtLogin()) {
+            this.roster.reload();
+        }
+
+        // Set presence to online.
+        if (config.isSendPresence()) {
+            packetWriter.sendPacket(new Presence(Presence.Type.available));
+        }
+
+        // Stores the authentication for future reconnection
+        config.setLoginInfo(username, password, resource);
+
+        // If debugging is enabled, change the the debug window title to include the
+        // name we are now logged-in as.
+        // If DEBUG_ENABLED was set to true AFTER the connection was created the debugger
+        // will be null
+        if (config.isDebuggerEnabled() && debugger != null) {
+            debugger.userHasLogged(user);
+        }
+    }
+
+    @Override
+    public synchronized void loginAnonymously() throws XMPPException {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (authenticated) {
+            throw new IllegalStateException("Already logged in to server.");
+        }
+
+        String response;
+        if (config.isSASLAuthenticationEnabled() &&
+                saslAuthentication.hasAnonymousAuthentication()) {
+            response = saslAuthentication.authenticateAnonymously();
+        }
+        else {
+            // Authenticate using Non-SASL
+            response = new NonSASLAuthentication(this).authenticateAnonymously();
+        }
+
+        // Set the user value.
+        this.user = response;
+        // Update the serviceName with the one returned by the server
+        config.setServiceName(StringUtils.parseServer(response));
+
+        // If compression is enabled then request the server to use stream compression
+        if (config.isCompressionEnabled()) {
+            useCompression();
+        }
+
+        // Set presence to online.
+        packetWriter.sendPacket(new Presence(Presence.Type.available));
+
+        // Indicate that we're now authenticated.
+        authenticated = true;
+        anonymous = true;
+
+        // If debugging is enabled, change the the debug window title to include the
+        // name we are now logged-in as.
+        // If DEBUG_ENABLED was set to true AFTER the connection was created the debugger
+        // will be null
+        if (config.isDebuggerEnabled() && debugger != null) {
+            debugger.userHasLogged(user);
+        }
+    }
+
+    public Roster getRoster() {
+        // synchronize against login()
+        synchronized(this) {
+            // if connection is authenticated the roster is already set by login() 
+            // or a previous call to getRoster()
+            if (!isAuthenticated() || isAnonymous()) {
+                if (roster == null) {
+                    roster = new Roster(this);
+                }
+                return roster;
+            }
+        }
+
+        if (!config.isRosterLoadedAtLogin()) {
+            roster.reload();
+        }
+        // If this is the first time the user has asked for the roster after calling
+        // login, we want to wait for the server to send back the user's roster. This
+        // behavior shields API users from having to worry about the fact that roster
+        // operations are asynchronous, although they'll still have to listen for
+        // changes to the roster. Note: because of this waiting logic, internal
+        // Smack code should be wary about calling the getRoster method, and may need to
+        // access the roster object directly.
+        if (!roster.rosterInitialized) {
+            try {
+                synchronized (roster) {
+                    long waitTime = SmackConfiguration.getPacketReplyTimeout();
+                    long start = System.currentTimeMillis();
+                    while (!roster.rosterInitialized) {
+                        if (waitTime <= 0) {
+                            break;
+                        }
+                        roster.wait(waitTime);
+                        long now = System.currentTimeMillis();
+                        waitTime -= now - start;
+                        start = now;
+                    }
+                }
+            }
+            catch (InterruptedException ie) {
+                // Ignore.
+            }
+        }
+        return roster;
+    }
+
+    public boolean isConnected() {
+        return connected;
+    }
+
+    public boolean isSecureConnection() {
+        return isUsingTLS();
+    }
+
+    public boolean isSocketClosed() {
+        return socketClosed;
+    }
+
+    public boolean isAuthenticated() {
+        return authenticated;
+    }
+
+    public boolean isAnonymous() {
+        return anonymous;
+    }
+
+    /**
+     * Closes the connection by setting presence to unavailable then closing the stream to
+     * the XMPP server. The shutdown logic will be used during a planned disconnection or when
+     * dealing with an unexpected disconnection. Unlike {@link #disconnect()} the connection's
+     * packet reader, packet writer, and {@link Roster} will not be removed; thus
+     * connection's state is kept.
+     *
+     * @param unavailablePresence the presence packet to send during shutdown.
+     */
+    protected void shutdown(Presence unavailablePresence) {
+        // Set presence to offline.
+        if (packetWriter != null) {
+                packetWriter.sendPacket(unavailablePresence);
+        }
+
+        this.setWasAuthenticated(authenticated);
+        authenticated = false;
+
+        if (packetReader != null) {
+                packetReader.shutdown();
+        }
+        if (packetWriter != null) {
+                packetWriter.shutdown();
+        }
+
+        // Wait 150 ms for processes to clean-up, then shutdown.
+        try {
+            Thread.sleep(150);
+        }
+        catch (Exception e) {
+            // Ignore.
+        }
+
+	// Set socketClosed to true. This will cause the PacketReader
+	// and PacketWriter to ingore any Exceptions that are thrown
+	// because of a read/write from/to a closed stream.
+	// It is *important* that this is done before socket.close()!
+        socketClosed = true;
+        try {
+                socket.close();
+        } catch (Exception e) {
+                e.printStackTrace();
+        }
+	// In most cases the close() should be successful, so set
+	// connected to false here.
+        connected = false;
+
+        // Close down the readers and writers.
+        if (reader != null) {
+            try {
+		// Should already be closed by the previous
+		// socket.close(). But just in case do it explicitly.
+                reader.close();
+            }
+            catch (Throwable ignore) { /* ignore */ }
+            reader = null;
+        }
+        if (writer != null) {
+            try {
+		// Should already be closed by the previous
+		// socket.close(). But just in case do it explicitly.
+                writer.close();
+            }
+            catch (Throwable ignore) { /* ignore */ }
+            writer = null;
+        }
+
+        // Make sure that the socket is really closed
+        try {
+	    // Does nothing if the socket is already closed
+            socket.close();
+        }
+        catch (Exception e) {
+            // Ignore.
+        }
+
+        saslAuthentication.init();
+    }
+
+    public synchronized void disconnect(Presence unavailablePresence) {
+        // If not connected, ignore this request.
+        PacketReader packetReader = this.packetReader;
+        PacketWriter packetWriter = this.packetWriter;
+        if (packetReader == null || packetWriter == null) {
+            return;
+        }
+
+        if (!isConnected()) {
+            return;
+        }
+
+        shutdown(unavailablePresence);
+
+        if (roster != null) {
+            roster.cleanup();
+            roster = null;
+        }
+        chatManager = null;
+
+        wasAuthenticated = false;
+
+        packetWriter.cleanup();
+        packetReader.cleanup();
+    }
+
+    public void sendPacket(Packet packet) {
+        if (!isConnected()) {
+            throw new IllegalStateException("Not connected to server.");
+        }
+        if (packet == null) {
+            throw new NullPointerException("Packet is null.");
+        }
+        packetWriter.sendPacket(packet);
+    }
+
+    /**
+     * Registers a packet interceptor with this connection. The interceptor will be
+     * invoked every time a packet is about to be sent by this connection. Interceptors
+     * may modify the packet to be sent. A packet filter determines which packets
+     * will be delivered to the interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to notify of packets about to be sent.
+     * @param packetFilter      the packet filter to use.
+     * @deprecated replaced by {@link Connection#addPacketInterceptor(PacketInterceptor, PacketFilter)}.
+     */
+    public void addPacketWriterInterceptor(PacketInterceptor packetInterceptor,
+            PacketFilter packetFilter) {
+        addPacketInterceptor(packetInterceptor, packetFilter);
+    }
+
+    /**
+     * Removes a packet interceptor.
+     *
+     * @param packetInterceptor the packet interceptor to remove.
+     * @deprecated replaced by {@link Connection#removePacketInterceptor(PacketInterceptor)}.
+     */
+    public void removePacketWriterInterceptor(PacketInterceptor packetInterceptor) {
+        removePacketInterceptor(packetInterceptor);
+    }
+
+    /**
+     * Registers a packet listener with this connection. The listener will be
+     * notified of every packet that this connection sends. A packet filter determines
+     * which packets will be delivered to the listener. Note that the thread
+     * that writes packets will be used to invoke the listeners. Therefore, each
+     * packet listener should complete all operations quickly or use a different
+     * thread for processing.
+     *
+     * @param packetListener the packet listener to notify of sent packets.
+     * @param packetFilter   the packet filter to use.
+     * @deprecated replaced by {@link #addPacketSendingListener(PacketListener, PacketFilter)}.
+     */
+    public void addPacketWriterListener(PacketListener packetListener, PacketFilter packetFilter) {
+        addPacketSendingListener(packetListener, packetFilter);
+    }
+
+    /**
+     * Removes a packet listener for sending packets from this connection.
+     *
+     * @param packetListener the packet listener to remove.
+     * @deprecated replaced by {@link #removePacketSendingListener(PacketListener)}.
+     */
+    public void removePacketWriterListener(PacketListener packetListener) {
+        removePacketSendingListener(packetListener);
+    }
+
+    private void connectUsingConfiguration(ConnectionConfiguration config) throws XMPPException {
+        XMPPException exception = null;
+        Iterator<HostAddress> it = config.getHostAddresses().iterator();
+        List<HostAddress> failedAddresses = new LinkedList<HostAddress>();
+        boolean xmppIOError = false;
+        while (it.hasNext()) {
+            exception = null;
+            HostAddress hostAddress = it.next();
+            String host = hostAddress.getFQDN();
+            int port = hostAddress.getPort();
+            try {
+                if (config.getSocketFactory() == null) {
+                    this.socket = new Socket(host, port);
+                }
+                else {
+                    this.socket = config.getSocketFactory().createSocket(host, port);
+                }
+            } catch (UnknownHostException uhe) {
+                String errorMessage = "Could not connect to " + host + ":" + port + ".";
+                exception = new XMPPException(errorMessage, new XMPPError(XMPPError.Condition.remote_server_timeout,
+                        errorMessage), uhe);
+            } catch (IOException ioe) {
+                String errorMessage = "XMPPError connecting to " + host + ":" + port + ".";
+                exception = new XMPPException(errorMessage, new XMPPError(XMPPError.Condition.remote_server_error,
+                        errorMessage), ioe);
+                xmppIOError = true;
+            }
+            if (exception == null) {
+                // We found a host to connect to, break here
+                config.setUsedHostAddress(hostAddress);
+                break;
+            }
+            hostAddress.setException(exception);
+            failedAddresses.add(hostAddress);
+            if (!it.hasNext()) {
+                // There are no more host addresses to try
+                // throw an exception and report all tried
+                // HostAddresses in the exception
+                StringBuilder sb = new StringBuilder();
+                for (HostAddress fha : failedAddresses) {
+                    sb.append(fha.getErrorMessage());
+                    sb.append("; ");
+                }
+                XMPPError xmppError;
+                if (xmppIOError) {
+                    xmppError = new XMPPError(XMPPError.Condition.remote_server_error);
+                }
+                else {
+                    xmppError = new XMPPError(XMPPError.Condition.remote_server_timeout);
+                }
+                throw new XMPPException(sb.toString(), xmppError);
+            }
+        }
+        socketClosed = false;
+        initConnection();
+    }
+
+    /**
+     * Initializes the connection by creating a packet reader and writer and opening a
+     * XMPP stream to the server.
+     *
+     * @throws XMPPException if establishing a connection to the server fails.
+     */
+    private void initConnection() throws XMPPException {
+        boolean isFirstInitialization = packetReader == null || packetWriter == null;
+        compressionHandler = null;
+        serverAckdCompression = false;
+
+        // Set the reader and writer instance variables
+        initReaderAndWriter();
+
+        try {
+            if (isFirstInitialization) {
+                packetWriter = new PacketWriter(this);
+                packetReader = new PacketReader(this);
+
+                // If debugging is enabled, we should start the thread that will listen for
+                // all packets and then log them.
+                if (config.isDebuggerEnabled()) {
+                    addPacketListener(debugger.getReaderListener(), null);
+                    if (debugger.getWriterListener() != null) {
+                        addPacketSendingListener(debugger.getWriterListener(), null);
+                    }
+                }
+            }
+            else {
+                packetWriter.init();
+                packetReader.init();
+            }
+
+            // Start the packet writer. This will open a XMPP stream to the server
+            packetWriter.startup();
+            // Start the packet reader. The startup() method will block until we
+            // get an opening stream packet back from server.
+            packetReader.startup();
+
+            // Make note of the fact that we're now connected.
+            connected = true;
+
+            if (isFirstInitialization) {
+                // Notify listeners that a new connection has been established
+                for (ConnectionCreationListener listener : getConnectionCreationListeners()) {
+                    listener.connectionCreated(this);
+                }
+            }
+            else if (!wasAuthenticated) {
+                notifyReconnection();
+            }
+
+        }
+        catch (XMPPException ex) {
+            // An exception occurred in setting up the connection. Make sure we shut down the
+            // readers and writers and close the socket.
+
+            if (packetWriter != null) {
+                try {
+                    packetWriter.shutdown();
+                }
+                catch (Throwable ignore) { /* ignore */ }
+                packetWriter = null;
+            }
+            if (packetReader != null) {
+                try {
+                    packetReader.shutdown();
+                }
+                catch (Throwable ignore) { /* ignore */ }
+                packetReader = null;
+            }
+            if (reader != null) {
+                try {
+                    reader.close();
+                }
+                catch (Throwable ignore) { /* ignore */ }
+                reader = null;
+            }
+            if (writer != null) {
+                try {
+                    writer.close();
+                }
+                catch (Throwable ignore) {  /* ignore */}
+                writer = null;
+            }
+            if (socket != null) {
+                try {
+                    socket.close();
+                }
+                catch (Exception e) { /* ignore */ }
+                socket = null;
+            }
+            this.setWasAuthenticated(authenticated);
+            chatManager = null;
+            authenticated = false;
+            connected = false;
+
+            throw ex;        // Everything stoppped. Now throw the exception.
+        }
+    }
+
+    private void initReaderAndWriter() throws XMPPException {
+        try {
+            if (compressionHandler == null) {
+                reader =
+                        new BufferedReader(new InputStreamReader(socket.getInputStream(), "UTF-8"));
+                writer = new BufferedWriter(
+                        new OutputStreamWriter(socket.getOutputStream(), "UTF-8"));
+            }
+            else {
+                try {
+                    OutputStream os = compressionHandler.getOutputStream(socket.getOutputStream());
+                    writer = new BufferedWriter(new OutputStreamWriter(os, "UTF-8"));
+
+                    InputStream is = compressionHandler.getInputStream(socket.getInputStream());
+                    reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
+                }
+                catch (Exception e) {
+                    e.printStackTrace();
+                    compressionHandler = null;
+                    reader = new BufferedReader(
+                            new InputStreamReader(socket.getInputStream(), "UTF-8"));
+                    writer = new BufferedWriter(
+                            new OutputStreamWriter(socket.getOutputStream(), "UTF-8"));
+                }
+            }
+        }
+        catch (IOException ioe) {
+            throw new XMPPException(
+                    "XMPPError establishing connection with server.",
+                    new XMPPError(XMPPError.Condition.remote_server_error,
+                            "XMPPError establishing connection with server."),
+                    ioe);
+        }
+
+        // If debugging is enabled, we open a window and write out all network traffic.
+        initDebugger();
+    }
+
+    /***********************************************
+     * TLS code below
+     **********************************************/
+
+    /**
+     * Returns true if the connection to the server has successfully negotiated TLS. Once TLS
+     * has been negotiatied the connection has been secured.
+     *
+     * @return true if the connection to the server has successfully negotiated TLS.
+     */
+    public boolean isUsingTLS() {
+        return usingTLS;
+    }
+
+    /**
+     * Notification message saying that the server supports TLS so confirm the server that we
+     * want to secure the connection.
+     *
+     * @param required true when the server indicates that TLS is required.
+     */
+    void startTLSReceived(boolean required) {
+        if (required && config.getSecurityMode() ==
+                ConnectionConfiguration.SecurityMode.disabled) {
+            notifyConnectionError(new IllegalStateException(
+                    "TLS required by server but not allowed by connection configuration"));
+            return;
+        }
+
+        if (config.getSecurityMode() == ConnectionConfiguration.SecurityMode.disabled) {
+            // Do not secure the connection using TLS since TLS was disabled
+            return;
+        }
+        try {
+            writer.write("<starttls xmlns=\"urn:ietf:params:xml:ns:xmpp-tls\"/>");
+            writer.flush();
+        }
+        catch (IOException e) {
+            notifyConnectionError(e);
+        }
+    }
+
+    /**
+     * The server has indicated that TLS negotiation can start. We now need to secure the
+     * existing plain connection and perform a handshake. This method won't return until the
+     * connection has finished the handshake or an error occured while securing the connection.
+     *
+     * @throws Exception if an exception occurs.
+     */
+    void proceedTLSReceived() throws Exception {
+        SSLContext context = this.config.getCustomSSLContext();
+        KeyStore ks = null;
+        KeyManager[] kms = null;
+        PasswordCallback pcb = null;
+
+        if(config.getCallbackHandler() == null) {
+           ks = null;
+        } else if (context == null) {
+            //System.out.println("Keystore type: "+configuration.getKeystoreType());
+            if(config.getKeystoreType().equals("NONE")) {
+                ks = null;
+                pcb = null;
+            }
+            else if(config.getKeystoreType().equals("PKCS11")) {
+                try {
+                    Constructor<?> c = Class.forName("sun.security.pkcs11.SunPKCS11").getConstructor(InputStream.class);
+                    String pkcs11Config = "name = SmartCard\nlibrary = "+config.getPKCS11Library();
+                    ByteArrayInputStream config = new ByteArrayInputStream(pkcs11Config.getBytes());
+                    Provider p = (Provider)c.newInstance(config);
+                    Security.addProvider(p);
+                    ks = KeyStore.getInstance("PKCS11",p);
+                    pcb = new PasswordCallback("PKCS11 Password: ",false);
+                    this.config.getCallbackHandler().handle(new Callback[]{pcb});
+                    ks.load(null,pcb.getPassword());
+                }
+                catch (Exception e) {
+                    ks = null;
+                    pcb = null;
+                }
+            }
+            else if(config.getKeystoreType().equals("Apple")) {
+                ks = KeyStore.getInstance("KeychainStore","Apple");
+                ks.load(null,null);
+                //pcb = new PasswordCallback("Apple Keychain",false);
+                //pcb.setPassword(null);
+            }
+            else {
+                ks = KeyStore.getInstance(config.getKeystoreType());
+                try {
+                    pcb = new PasswordCallback("Keystore Password: ",false);
+                    config.getCallbackHandler().handle(new Callback[]{pcb});
+                    ks.load(new FileInputStream(config.getKeystorePath()), pcb.getPassword());
+                }
+                catch(Exception e) {
+                    ks = null;
+                    pcb = null;
+                }
+            }
+            KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
+            try {
+                if(pcb == null) {
+                    kmf.init(ks,null);
+                } else {
+                    kmf.init(ks,pcb.getPassword());
+                    pcb.clearPassword();
+                }
+                kms = kmf.getKeyManagers();
+            } catch (NullPointerException npe) {
+                kms = null;
+            }
+        }
+
+        // Verify certificate presented by the server
+        if (context == null) {
+            context = SSLContext.getInstance("TLS");
+            context.init(kms, new javax.net.ssl.TrustManager[] { new ServerTrustManager(getServiceName(), config) },
+                    new java.security.SecureRandom());
+        }
+        Socket plain = socket;
+        // Secure the plain connection
+        socket = context.getSocketFactory().createSocket(plain,
+                plain.getInetAddress().getHostAddress(), plain.getPort(), true);
+        socket.setSoTimeout(0);
+        socket.setKeepAlive(true);
+        // Initialize the reader and writer with the new secured version
+        initReaderAndWriter();
+        // Proceed to do the handshake
+        ((SSLSocket) socket).startHandshake();
+        //if (((SSLSocket) socket).getWantClientAuth()) {
+        //    System.err.println("Connection wants client auth");
+        //}
+        //else if (((SSLSocket) socket).getNeedClientAuth()) {
+        //    System.err.println("Connection needs client auth");
+        //}
+        //else {
+        //    System.err.println("Connection does not require client auth");
+       // }
+        // Set that TLS was successful
+        usingTLS = true;
+
+        // Set the new  writer to use
+        packetWriter.setWriter(writer);
+        // Send a new opening stream to the server
+        packetWriter.openStream();
+    }
+
+    /**
+     * Sets the available stream compression methods offered by the server.
+     *
+     * @param methods compression methods offered by the server.
+     */
+    void setAvailableCompressionMethods(Collection<String> methods) {
+        compressionMethods = methods;
+    }
+
+    /**
+     * Returns the compression handler that can be used for one compression methods offered by the server.
+     * 
+     * @return a instance of XMPPInputOutputStream or null if no suitable instance was found
+     * 
+     */
+    private XMPPInputOutputStream maybeGetCompressionHandler() {
+        if (compressionMethods != null) {
+            for (XMPPInputOutputStream handler : compressionHandlers) {
+                if (!handler.isSupported())
+                    continue;
+
+                String method = handler.getCompressionMethod();
+                if (compressionMethods.contains(method))
+                    return handler;
+            }
+        }
+        return null;
+    }
+
+    public boolean isUsingCompression() {
+        return compressionHandler != null && serverAckdCompression;
+    }
+
+    /**
+     * Starts using stream compression that will compress network traffic. Traffic can be
+     * reduced up to 90%. Therefore, stream compression is ideal when using a slow speed network
+     * connection. However, the server and the client will need to use more CPU time in order to
+     * un/compress network data so under high load the server performance might be affected.<p>
+     * <p/>
+     * Stream compression has to have been previously offered by the server. Currently only the
+     * zlib method is supported by the client. Stream compression negotiation has to be done
+     * before authentication took place.<p>
+     * <p/>
+     * Note: to use stream compression the smackx.jar file has to be present in the classpath.
+     *
+     * @return true if stream compression negotiation was successful.
+     */
+    private boolean useCompression() {
+        // If stream compression was offered by the server and we want to use
+        // compression then send compression request to the server
+        if (authenticated) {
+            throw new IllegalStateException("Compression should be negotiated before authentication.");
+        }
+
+        if ((compressionHandler = maybeGetCompressionHandler()) != null) {
+            requestStreamCompression(compressionHandler.getCompressionMethod());
+            // Wait until compression is being used or a timeout happened
+            synchronized (this) {
+                try {
+                    this.wait(SmackConfiguration.getPacketReplyTimeout() * 5);
+                }
+                catch (InterruptedException e) {
+                    // Ignore.
+                }
+            }
+            return isUsingCompression();
+        }
+        return false;
+    }
+
+    /**
+     * Request the server that we want to start using stream compression. When using TLS
+     * then negotiation of stream compression can only happen after TLS was negotiated. If TLS
+     * compression is being used the stream compression should not be used.
+     */
+    private void requestStreamCompression(String method) {
+        try {
+            writer.write("<compress xmlns='http://jabber.org/protocol/compress'>");
+            writer.write("<method>" + method + "</method></compress>");
+            writer.flush();
+        }
+        catch (IOException e) {
+            notifyConnectionError(e);
+        }
+    }
+
+    /**
+     * Start using stream compression since the server has acknowledged stream compression.
+     *
+     * @throws Exception if there is an exception starting stream compression.
+     */
+    void startStreamCompression() throws Exception {
+        serverAckdCompression = true;
+        // Initialize the reader and writer with the new secured version
+        initReaderAndWriter();
+
+        // Set the new  writer to use
+        packetWriter.setWriter(writer);
+        // Send a new opening stream to the server
+        packetWriter.openStream();
+        // Notify that compression is being used
+        synchronized (this) {
+            this.notify();
+        }
+    }
+
+    /**
+     * Notifies the XMPP connection that stream compression was denied so that
+     * the connection process can proceed.
+     */
+    void streamCompressionDenied() {
+        synchronized (this) {
+            this.notify();
+        }
+    }
+
+    /**
+     * Establishes a connection to the XMPP server and performs an automatic login
+     * only if the previous connection state was logged (authenticated). It basically
+     * creates and maintains a socket connection to the server.<p>
+     * <p/>
+     * Listeners will be preserved from a previous connection if the reconnection
+     * occurs after an abrupt termination.
+     *
+     * @throws XMPPException if an error occurs while trying to establish the connection.
+     *      Two possible errors can occur which will be wrapped by an XMPPException --
+     *      UnknownHostException (XMPP error code 504), and IOException (XMPP error code
+     *      502). The error codes and wrapped exceptions can be used to present more
+     *      appropriate error messages to end-users.
+     */
+    public void connect() throws XMPPException {
+        // Establishes the connection, readers and writers
+        connectUsingConfiguration(config);
+        // Automatically makes the login if the user was previously connected successfully
+        // to the server and the connection was terminated abruptly
+        if (connected && wasAuthenticated) {
+            // Make the login
+            if (isAnonymous()) {
+                // Make the anonymous login
+                loginAnonymously();
+            }
+            else {
+                login(config.getUsername(), config.getPassword(), config.getResource());
+            }
+            notifyReconnection();
+        }
+    }
+
+    /**
+     * Sets whether the connection has already logged in the server.
+     *
+     * @param wasAuthenticated true if the connection has already been authenticated.
+     */
+    private void setWasAuthenticated(boolean wasAuthenticated) {
+        if (!this.wasAuthenticated) {
+            this.wasAuthenticated = wasAuthenticated;
+        }
+    }
+
+	@Override
+	public void setRosterStorage(RosterStorage storage)
+			throws IllegalStateException {
+		if(roster!=null){
+			throw new IllegalStateException("Roster is already initialized");
+		}
+		this.rosterStorage = storage;
+	}
+
+    /**
+     * Sends out a notification that there was an error with the connection
+     * and closes the connection. Also prints the stack trace of the given exception
+     *
+     * @param e the exception that causes the connection close event.
+     */
+    synchronized void notifyConnectionError(Exception e) {
+        // Listeners were already notified of the exception, return right here.
+        if (packetReader.done && packetWriter.done) return;
+
+        packetReader.done = true;
+        packetWriter.done = true;
+        // Closes the connection temporary. A reconnection is possible
+        shutdown(new Presence(Presence.Type.unavailable));
+        // Print the stack trace to help catch the problem
+        e.printStackTrace();
+        // Notify connection listeners of the error.
+        for (ConnectionListener listener : getConnectionListeners()) {
+            try {
+                listener.connectionClosedOnError(e);
+            }
+            catch (Exception e2) {
+                // Catch and print any exception so we can recover
+                // from a faulty listener
+                e2.printStackTrace();
+            }
+        }
+    }
+    
+
+    /**
+     * Sends a notification indicating that the connection was reconnected successfully.
+     */
+    protected void notifyReconnection() {
+        // Notify connection listeners of the reconnection.
+        for (ConnectionListener listener : getConnectionListeners()) {
+            try {
+                listener.reconnectionSuccessful();
+            }
+            catch (Exception e) {
+                // Catch and print any exception so we can recover
+                // from a faulty listener
+                e.printStackTrace();
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/XMPPException.java b/src/org/jivesoftware/smack/XMPPException.java
new file mode 100644
index 0000000..6da24c2
--- /dev/null
+++ b/src/org/jivesoftware/smack/XMPPException.java
@@ -0,0 +1,219 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack;
+
+import org.jivesoftware.smack.packet.StreamError;
+import org.jivesoftware.smack.packet.XMPPError;
+
+import java.io.PrintStream;
+import java.io.PrintWriter;
+
+/**
+ * A generic exception that is thrown when an error occurs performing an
+ * XMPP operation. XMPP servers can respond to error conditions with an error code
+ * and textual description of the problem, which are encapsulated in the XMPPError
+ * class. When appropriate, an XMPPError instance is attached instances of this exception.<p>
+ *
+ * When a stream error occured, the server will send a stream error to the client before
+ * closing the connection. Stream errors are unrecoverable errors. When a stream error
+ * is sent to the client an XMPPException will be thrown containing the StreamError sent
+ * by the server.
+ *
+ * @see XMPPError
+ * @author Matt Tucker
+ */
+public class XMPPException extends Exception {
+
+    private StreamError streamError = null;
+    private XMPPError error = null;
+    private Throwable wrappedThrowable = null;
+
+    /**
+     * Creates a new XMPPException.
+     */
+    public XMPPException() {
+        super();
+    }
+
+    /**
+     * Creates a new XMPPException with a description of the exception.
+     *
+     * @param message description of the exception.
+     */
+    public XMPPException(String message) {
+        super(message);
+    }
+
+    /**
+     * Creates a new XMPPException with the Throwable that was the root cause of the
+     * exception.
+     *
+     * @param wrappedThrowable the root cause of the exception.
+     */
+    public XMPPException(Throwable wrappedThrowable) {
+        super();
+        this.wrappedThrowable = wrappedThrowable;
+    }
+
+    /**
+     * Cretaes a new XMPPException with the stream error that was the root case of the
+     * exception. When a stream error is received from the server then the underlying
+     * TCP connection will be closed by the server.
+     *
+     * @param streamError the root cause of the exception.
+     */
+    public XMPPException(StreamError streamError) {
+        super();
+        this.streamError = streamError;
+    }
+
+    /**
+     * Cretaes a new XMPPException with the XMPPError that was the root case of the
+     * exception.
+     *
+     * @param error the root cause of the exception.
+     */
+    public XMPPException(XMPPError error) {
+        super();
+        this.error = error;
+    }
+
+    /**
+     * Creates a new XMPPException with a description of the exception and the
+     * Throwable that was the root cause of the exception.
+     *
+     * @param message a description of the exception.
+     * @param wrappedThrowable the root cause of the exception.
+     */
+    public XMPPException(String message, Throwable wrappedThrowable) {
+        super(message);
+        this.wrappedThrowable = wrappedThrowable;
+    }
+
+    /**
+     * Creates a new XMPPException with a description of the exception, an XMPPError,
+     * and the Throwable that was the root cause of the exception.
+     *
+     * @param message a description of the exception.
+     * @param error the root cause of the exception.
+     * @param wrappedThrowable the root cause of the exception.
+     */
+    public XMPPException(String message, XMPPError error, Throwable wrappedThrowable) {
+        super(message);
+        this.error = error;
+        this.wrappedThrowable = wrappedThrowable;
+    }
+
+    /**
+     * Creates a new XMPPException with a description of the exception and the
+     * XMPPException that was the root cause of the exception.
+     *
+     * @param message a description of the exception.
+     * @param error the root cause of the exception.
+     */
+    public XMPPException(String message, XMPPError error) {
+        super(message);
+        this.error = error;
+    }
+
+    /**
+     * Returns the XMPPError asscociated with this exception, or <tt>null</tt> if there
+     * isn't one.
+     *
+     * @return the XMPPError asscociated with this exception.
+     */
+    public XMPPError getXMPPError() {
+        return error;
+    }
+
+    /**
+     * Returns the StreamError asscociated with this exception, or <tt>null</tt> if there
+     * isn't one. The underlying TCP connection is closed by the server after sending the
+     * stream error to the client.
+     *
+     * @return the StreamError asscociated with this exception.
+     */
+    public StreamError getStreamError() {
+        return streamError;
+    }
+
+    /**
+     * Returns the Throwable asscociated with this exception, or <tt>null</tt> if there
+     * isn't one.
+     *
+     * @return the Throwable asscociated with this exception.
+     */
+    public Throwable getWrappedThrowable() {
+        return wrappedThrowable;
+    }
+
+    public void printStackTrace() {
+        printStackTrace(System.err);
+    }
+
+    public void printStackTrace(PrintStream out) {
+        super.printStackTrace(out);
+        if (wrappedThrowable != null) {
+            out.println("Nested Exception: ");
+            wrappedThrowable.printStackTrace(out);
+        }
+    }
+
+    public void printStackTrace(PrintWriter out) {
+        super.printStackTrace(out);
+        if (wrappedThrowable != null) {
+            out.println("Nested Exception: ");
+            wrappedThrowable.printStackTrace(out);
+        }
+    }
+
+    public String getMessage() {
+        String msg = super.getMessage();
+        // If the message was not set, but there is an XMPPError, return the
+        // XMPPError as the message.
+        if (msg == null && error != null) {
+            return error.toString();
+        }
+        else if (msg == null && streamError != null) {
+            return streamError.toString();
+        }
+        return msg;
+    }
+
+    public String toString() {
+        StringBuilder buf = new StringBuilder();
+        String message = super.getMessage();
+        if (message != null) {
+            buf.append(message).append(": ");
+        }
+        if (error != null) {
+            buf.append(error);
+        }
+        if (streamError != null) {
+            buf.append(streamError);
+        }
+        if (wrappedThrowable != null) {
+            buf.append("\n  -- caused by: ").append(wrappedThrowable);
+        }
+
+        return buf.toString();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/compression/Java7ZlibInputOutputStream.java b/src/org/jivesoftware/smack/compression/Java7ZlibInputOutputStream.java
new file mode 100644
index 0000000..dc50451
--- /dev/null
+++ b/src/org/jivesoftware/smack/compression/Java7ZlibInputOutputStream.java
@@ -0,0 +1,126 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.compression;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.zip.Deflater;
+import java.util.zip.DeflaterOutputStream;
+import java.util.zip.Inflater;
+import java.util.zip.InflaterInputStream;
+
+/**
+ * This class provides XMPP "zlib" compression with the help of the Deflater class of the Java API. Note that the method
+ * needed is available since Java7, so it will only work with Java7 or higher (hence it's name).
+ * 
+ * @author Florian Schmaus
+ * @see <a
+ * href="http://docs.oracle.com/javase/7/docs/api/java/util/zip/Deflater.html#deflate(byte[], int, int, int)">The
+ * required deflate() method</a>
+ * 
+ */
+public class Java7ZlibInputOutputStream extends XMPPInputOutputStream {
+    private final static Method method;
+    private final static boolean supported;
+    private final static int compressionLevel = Deflater.DEFAULT_STRATEGY;
+
+    static {
+        Method m = null;
+        try {
+            m = Deflater.class.getMethod("deflate", byte[].class, int.class, int.class, int.class);
+        } catch (SecurityException e) {
+        } catch (NoSuchMethodException e) {
+        }
+        method = m;
+        supported = (method != null);
+    }
+
+    public Java7ZlibInputOutputStream() {
+        compressionMethod = "zlib";
+    }
+
+    @Override
+    public boolean isSupported() {
+        return supported;
+    }
+
+    @Override
+    public InputStream getInputStream(InputStream inputStream) {
+        return new InflaterInputStream(inputStream, new Inflater(), 512) {
+            /**
+             * Provide a more InputStream compatible version. A return value of 1 means that it is likely to read one
+             * byte without blocking, 0 means that the system is known to block for more input.
+             * 
+             * @return 0 if no data is available, 1 otherwise
+             * @throws IOException
+             */
+            @Override
+            public int available() throws IOException {
+                /*
+                 * aSmack related remark (where KXmlParser is used):
+                 * This is one of the funny code blocks. InflaterInputStream.available violates the contract of
+                 * InputStream.available, which breaks kXML2.
+                 * 
+                 * I'm not sure who's to blame, oracle/sun for a broken api or the google guys for mixing a sun bug with
+                 * a xml reader that can't handle it....
+                 * 
+                 * Anyway, this simple if breaks suns distorted reality, but helps to use the api as intended.
+                 */
+                if (inf.needsInput()) {
+                    return 0;
+                }
+                return super.available();
+            }
+        };
+    }
+
+    @Override
+    public OutputStream getOutputStream(OutputStream outputStream) {
+        return new DeflaterOutputStream(outputStream, new Deflater(compressionLevel)) {
+            public void flush() throws IOException {
+                if (!supported) {
+                    super.flush();
+                    return;
+                }
+                int count = 0;
+                if (!def.needsInput()) {
+                    do {
+                        count = def.deflate(buf, 0, buf.length);
+                        out.write(buf, 0, count);
+                    } while (count > 0);
+                    out.flush();
+                }
+                try {
+                    do {
+                        count = (Integer) method.invoke(def, buf, 0, buf.length, 2);
+                        out.write(buf, 0, count);
+                    } while (count > 0);
+                } catch (IllegalArgumentException e) {
+                    throw new IOException("Can't flush");
+                } catch (IllegalAccessException e) {
+                    throw new IOException("Can't flush");
+                } catch (InvocationTargetException e) {
+                    throw new IOException("Can't flush");
+                }
+                super.flush();
+            }
+        };
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/compression/JzlibInputOutputStream.java b/src/org/jivesoftware/smack/compression/JzlibInputOutputStream.java
new file mode 100644
index 0000000..7db0773
--- /dev/null
+++ b/src/org/jivesoftware/smack/compression/JzlibInputOutputStream.java
@@ -0,0 +1,75 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.compression;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+/**
+ * This class provides XMPP "zlib" compression with the help of JZLib. Note that jzlib-1.0.7 must be used (i.e. in the
+ * classpath), newer versions won't work!
+ * 
+ * @author Florian Schmaus
+ * @see <a href="http://www.jcraft.com/jzlib/">JZLib</a>
+ * 
+ */
+public class JzlibInputOutputStream extends XMPPInputOutputStream {
+
+    private static Class<?> zoClass = null;
+    private static Class<?> ziClass = null;
+
+    static {
+        try {
+            zoClass = Class.forName("com.jcraft.jzlib.ZOutputStream");
+            ziClass = Class.forName("com.jcraft.jzlib.ZInputStream");
+        } catch (ClassNotFoundException e) {
+        }
+    }
+
+    public JzlibInputOutputStream() {
+        compressionMethod = "zlib";
+    }
+
+    @Override
+    public boolean isSupported() {
+        return (zoClass != null && ziClass != null);
+    }
+
+    @Override
+    public InputStream getInputStream(InputStream inputStream) throws SecurityException, NoSuchMethodException,
+            IllegalArgumentException, IllegalAccessException, InvocationTargetException, InstantiationException {
+        Constructor<?> constructor = ziClass.getConstructor(InputStream.class);
+        Object in = constructor.newInstance(inputStream);
+
+        Method method = ziClass.getMethod("setFlushMode", Integer.TYPE);
+        method.invoke(in, 2);
+        return (InputStream) in;
+    }
+
+    @Override
+    public OutputStream getOutputStream(OutputStream outputStream) throws SecurityException, NoSuchMethodException,
+            IllegalArgumentException, InstantiationException, IllegalAccessException, InvocationTargetException {
+        Constructor<?> constructor = zoClass.getConstructor(OutputStream.class, Integer.TYPE);
+        Object out = constructor.newInstance(outputStream, 9);
+
+        Method method = zoClass.getMethod("setFlushMode", Integer.TYPE);
+        method.invoke(out, 2);
+        return (OutputStream) out;
+    }
+}
diff --git a/src/org/jivesoftware/smack/compression/XMPPInputOutputStream.java b/src/org/jivesoftware/smack/compression/XMPPInputOutputStream.java
new file mode 100644
index 0000000..d44416a
--- /dev/null
+++ b/src/org/jivesoftware/smack/compression/XMPPInputOutputStream.java
@@ -0,0 +1,33 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.compression;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+
+public abstract class XMPPInputOutputStream {
+    protected String compressionMethod;
+
+    public String getCompressionMethod() {
+        return compressionMethod;
+    }
+
+    public abstract boolean isSupported();
+
+    public abstract InputStream getInputStream(InputStream inputStream) throws Exception;
+
+    public abstract OutputStream getOutputStream(OutputStream outputStream) throws Exception;
+}
diff --git a/src/org/jivesoftware/smack/debugger/ConsoleDebugger.java b/src/org/jivesoftware/smack/debugger/ConsoleDebugger.java
new file mode 100644
index 0000000..7e078b4
--- /dev/null
+++ b/src/org/jivesoftware/smack/debugger/ConsoleDebugger.java
@@ -0,0 +1,198 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.debugger;
+
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.*;
+
+import java.io.Reader;
+import java.io.Writer;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * Very simple debugger that prints to the console (stdout) the sent and received stanzas. Use
+ * this debugger with caution since printing to the console is an expensive operation that may
+ * even block the thread since only one thread may print at a time.<p>
+ * <p/>
+ * It is possible to not only print the raw sent and received stanzas but also the interpreted
+ * packets by Smack. By default interpreted packets won't be printed. To enable this feature
+ * just change the <tt>printInterpreted</tt> static variable to <tt>true</tt>.
+ *
+ * @author Gaston Dombiak
+ */
+public class ConsoleDebugger implements SmackDebugger {
+
+    public static boolean printInterpreted = false;
+    private SimpleDateFormat dateFormatter = new SimpleDateFormat("hh:mm:ss aaa");
+
+    private Connection connection = null;
+
+    private PacketListener listener = null;
+    private ConnectionListener connListener = null;
+
+    private Writer writer;
+    private Reader reader;
+    private ReaderListener readerListener;
+    private WriterListener writerListener;
+
+    public ConsoleDebugger(Connection connection, Writer writer, Reader reader) {
+        this.connection = connection;
+        this.writer = writer;
+        this.reader = reader;
+        createDebug();
+    }
+
+    /**
+     * Creates the listeners that will print in the console when new activity is detected.
+     */
+    private void createDebug() {
+        // Create a special Reader that wraps the main Reader and logs data to the GUI.
+        ObservableReader debugReader = new ObservableReader(reader);
+        readerListener = new ReaderListener() {
+            public void read(String str) {
+                System.out.println(
+                        dateFormatter.format(new Date()) + " RCV  (" + connection.hashCode() +
+                        "): " +
+                        str);
+            }
+        };
+        debugReader.addReaderListener(readerListener);
+
+        // Create a special Writer that wraps the main Writer and logs data to the GUI.
+        ObservableWriter debugWriter = new ObservableWriter(writer);
+        writerListener = new WriterListener() {
+            public void write(String str) {
+                System.out.println(
+                        dateFormatter.format(new Date()) + " SENT (" + connection.hashCode() +
+                        "): " +
+                        str);
+            }
+        };
+        debugWriter.addWriterListener(writerListener);
+
+        // Assign the reader/writer objects to use the debug versions. The packet reader
+        // and writer will use the debug versions when they are created.
+        reader = debugReader;
+        writer = debugWriter;
+
+        // Create a thread that will listen for all incoming packets and write them to
+        // the GUI. This is what we call "interpreted" packet data, since it's the packet
+        // data as Smack sees it and not as it's coming in as raw XML.
+        listener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                if (printInterpreted) {
+                    System.out.println(
+                            dateFormatter.format(new Date()) + " RCV PKT (" +
+                            connection.hashCode() +
+                            "): " +
+                            packet.toXML());
+                }
+            }
+        };
+
+        connListener = new ConnectionListener() {
+            public void connectionClosed() {
+                System.out.println(
+                        dateFormatter.format(new Date()) + " Connection closed (" +
+                        connection.hashCode() +
+                        ")");
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                System.out.println(
+                        dateFormatter.format(new Date()) +
+                        " Connection closed due to an exception (" +
+                        connection.hashCode() +
+                        ")");
+                e.printStackTrace();
+            }
+            public void reconnectionFailed(Exception e) {
+                System.out.println(
+                        dateFormatter.format(new Date()) +
+                        " Reconnection failed due to an exception (" +
+                        connection.hashCode() +
+                        ")");
+                e.printStackTrace();
+            }
+            public void reconnectionSuccessful() {
+                System.out.println(
+                        dateFormatter.format(new Date()) + " Connection reconnected (" +
+                        connection.hashCode() +
+                        ")");
+            }
+            public void reconnectingIn(int seconds) {
+                System.out.println(
+                        dateFormatter.format(new Date()) + " Connection (" +
+                        connection.hashCode() +
+                        ") will reconnect in " + seconds);
+            }
+        };
+    }
+
+    public Reader newConnectionReader(Reader newReader) {
+        ((ObservableReader)reader).removeReaderListener(readerListener);
+        ObservableReader debugReader = new ObservableReader(newReader);
+        debugReader.addReaderListener(readerListener);
+        reader = debugReader;
+        return reader;
+    }
+
+    public Writer newConnectionWriter(Writer newWriter) {
+        ((ObservableWriter)writer).removeWriterListener(writerListener);
+        ObservableWriter debugWriter = new ObservableWriter(newWriter);
+        debugWriter.addWriterListener(writerListener);
+        writer = debugWriter;
+        return writer;
+    }
+
+    public void userHasLogged(String user) {
+        boolean isAnonymous = "".equals(StringUtils.parseName(user));
+        String title =
+                "User logged (" + connection.hashCode() + "): "
+                + (isAnonymous ? "" : StringUtils.parseBareAddress(user))
+                + "@"
+                + connection.getServiceName()
+                + ":"
+                + connection.getPort();
+        title += "/" + StringUtils.parseResource(user);
+        System.out.println(title);
+        // Add the connection listener to the connection so that the debugger can be notified
+        // whenever the connection is closed.
+        connection.addConnectionListener(connListener);
+    }
+
+    public Reader getReader() {
+        return reader;
+    }
+
+    public Writer getWriter() {
+        return writer;
+    }
+
+    public PacketListener getReaderListener() {
+        return listener;
+    }
+
+    public PacketListener getWriterListener() {
+        return null;
+    }
+}
diff --git a/src/org/jivesoftware/smack/debugger/SmackDebugger.java b/src/org/jivesoftware/smack/debugger/SmackDebugger.java
new file mode 100644
index 0000000..562720b
--- /dev/null
+++ b/src/org/jivesoftware/smack/debugger/SmackDebugger.java
@@ -0,0 +1,98 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.debugger;
+
+import java.io.*;
+
+import org.jivesoftware.smack.*;
+
+/**
+ * Interface that allows for implementing classes to debug XML traffic. That is a GUI window that 
+ * displays XML traffic.<p>
+ * 
+ * Every implementation of this interface <b>must</b> have a public constructor with the following 
+ * arguments: Connection, Writer, Reader.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface SmackDebugger {
+
+    /**
+     * Called when a user has logged in to the server. The user could be an anonymous user, this 
+     * means that the user would be of the form host/resource instead of the form 
+     * user@host/resource.
+     * 
+     * @param user the user@host/resource that has just logged in
+     */
+    public abstract void userHasLogged(String user);
+
+    /**
+     * Returns the special Reader that wraps the main Reader and logs data to the GUI.
+     * 
+     * @return the special Reader that wraps the main Reader and logs data to the GUI.
+     */
+    public abstract Reader getReader();
+
+    /**
+     * Returns the special Writer that wraps the main Writer and logs data to the GUI.
+     * 
+     * @return the special Writer that wraps the main Writer and logs data to the GUI.
+     */
+    public abstract Writer getWriter();
+
+    /**
+     * Returns a new special Reader that wraps the new connection Reader. The connection
+     * has been secured so the connection is using a new reader and writer. The debugger
+     * needs to wrap the new reader and writer to keep being notified of the connection
+     * traffic.
+     *
+     * @return a new special Reader that wraps the new connection Reader.
+     */
+    public abstract Reader newConnectionReader(Reader reader);
+
+    /**
+     * Returns a new special Writer that wraps the new connection Writer. The connection
+     * has been secured so the connection is using a new reader and writer. The debugger
+     * needs to wrap the new reader and writer to keep being notified of the connection
+     * traffic.
+     *
+     * @return a new special Writer that wraps the new connection Writer.
+     */
+    public abstract Writer newConnectionWriter(Writer writer);
+
+    /**
+     * Returns the thread that will listen for all incoming packets and write them to the GUI. 
+     * This is what we call "interpreted" packet data, since it's the packet data as Smack sees 
+     * it and not as it's coming in as raw XML.
+     * 
+     * @return the PacketListener that will listen for all incoming packets and write them to 
+     * the GUI
+     */
+    public abstract PacketListener getReaderListener();
+
+    /**
+     * Returns the thread that will listen for all outgoing packets and write them to the GUI. 
+     * 
+     * @return the PacketListener that will listen for all sent packets and write them to 
+     * the GUI
+     */
+    public abstract PacketListener getWriterListener();
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/debugger/package.html b/src/org/jivesoftware/smack/debugger/package.html
new file mode 100644
index 0000000..afb861f
--- /dev/null
+++ b/src/org/jivesoftware/smack/debugger/package.html
@@ -0,0 +1 @@
+<body>Core debugger functionality.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/filter/AndFilter.java b/src/org/jivesoftware/smack/filter/AndFilter.java
new file mode 100644
index 0000000..847b618
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/AndFilter.java
@@ -0,0 +1,91 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+import java.util.List;
+import java.util.ArrayList;
+
+/**
+ * Implements the logical AND operation over two or more packet filters.
+ * In other words, packets pass this filter if they pass <b>all</b> of the filters.
+ *
+ * @author Matt Tucker
+ */
+public class AndFilter implements PacketFilter {
+
+    /**
+     * The list of filters.
+     */
+    private List<PacketFilter> filters = new ArrayList<PacketFilter>();
+
+    /**
+     * Creates an empty AND filter. Filters should be added using the
+     * {@link #addFilter(PacketFilter)} method.
+     */
+    public AndFilter() {
+
+    }
+
+    /**
+     * Creates an AND filter using the specified filters.
+     *
+     * @param filters the filters to add.
+     */
+    public AndFilter(PacketFilter... filters) {
+        if (filters == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        for(PacketFilter filter : filters) {
+            if(filter == null) {
+                throw new IllegalArgumentException("Parameter cannot be null.");
+            }
+            this.filters.add(filter);
+        }
+    }
+
+    /**
+     * Adds a filter to the filter list for the AND operation. A packet
+     * will pass the filter if all of the filters in the list accept it.
+     *
+     * @param filter a filter to add to the filter list.
+     */
+    public void addFilter(PacketFilter filter) {
+        if (filter == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        filters.add(filter);
+    }
+
+    public boolean accept(Packet packet) {
+        for (PacketFilter filter : filters) {
+            if (!filter.accept(packet)) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    public String toString() {
+        return filters.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/FromContainsFilter.java b/src/org/jivesoftware/smack/filter/FromContainsFilter.java
new file mode 100644
index 0000000..f8e9e97
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/FromContainsFilter.java
@@ -0,0 +1,54 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets where the "from" field contains a specified value.
+ *
+ * @author Matt Tucker
+ */
+public class FromContainsFilter implements PacketFilter {
+
+    private String from;
+
+    /**
+     * Creates a "from" contains filter using the "from" field part.
+     *
+     * @param from the from field value the packet must contain.
+     */
+    public FromContainsFilter(String from) {
+        if (from == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        this.from = from.toLowerCase();
+    }
+
+    public boolean accept(Packet packet) {
+        if (packet.getFrom() == null) {
+            return false;
+        }
+        else {
+            return packet.getFrom().toLowerCase().indexOf(from) != -1;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/filter/FromMatchesFilter.java b/src/org/jivesoftware/smack/filter/FromMatchesFilter.java
new file mode 100644
index 0000000..e1dfa6c
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/FromMatchesFilter.java
@@ -0,0 +1,75 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * Filter for packets where the "from" field exactly matches a specified JID. If the specified
+ * address is a bare JID then the filter will match any address whose bare JID matches the
+ * specified JID. But if the specified address is a full JID then the filter will only match
+ * if the sender of the packet matches the specified resource.
+ *
+ * @author Gaston Dombiak
+ */
+public class FromMatchesFilter implements PacketFilter {
+
+    private String address;
+    /**
+     * Flag that indicates if the checking will be done against bare JID addresses or full JIDs.
+     */
+    private boolean matchBareJID = false;
+
+    /**
+     * Creates a "from" filter using the "from" field part. If the specified address is a bare JID
+     * then the filter will match any address whose bare JID matches the specified JID. But if the
+     * specified address is a full JID then the filter will only match if the sender of the packet
+     * matches the specified resource.
+     *
+     * @param address the from field value the packet must match. Could be a full or bare JID.
+     */
+    public FromMatchesFilter(String address) {
+        if (address == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        this.address = address.toLowerCase();
+        matchBareJID = "".equals(StringUtils.parseResource(address));
+    }
+
+    public boolean accept(Packet packet) {
+        if (packet.getFrom() == null) {
+            return false;
+        }
+        else if (matchBareJID) {
+            // Check if the bare JID of the sender of the packet matches the specified JID
+            return packet.getFrom().toLowerCase().startsWith(address);
+        }
+        else {
+            // Check if the full JID of the sender of the packet matches the specified JID
+            return address.equals(packet.getFrom().toLowerCase());
+        }
+    }
+
+    public String toString() {
+        return "FromMatchesFilter: " + address;
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/IQTypeFilter.java b/src/org/jivesoftware/smack/filter/IQTypeFilter.java
new file mode 100644
index 0000000..dbab1c3
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/IQTypeFilter.java
@@ -0,0 +1,48 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * A filter for IQ packet types. Returns true only if the packet is an IQ packet
+ * and it matches the type provided in the constructor.
+ * 
+ * @author Alexander Wenckus
+ * 
+ */
+public class IQTypeFilter implements PacketFilter {
+
+	private IQ.Type type;
+
+	public IQTypeFilter(IQ.Type type) {
+		this.type = type;
+	}
+
+	/*
+	 * (non-Javadoc)
+	 * 
+	 * @see org.jivesoftware.smack.filter.PacketFilter#accept(org.jivesoftware.smack.packet.Packet)
+	 */
+	public boolean accept(Packet packet) {
+		return (packet instanceof IQ && ((IQ) packet).getType().equals(type));
+	}
+}
diff --git a/src/org/jivesoftware/smack/filter/MessageTypeFilter.java b/src/org/jivesoftware/smack/filter/MessageTypeFilter.java
new file mode 100644
index 0000000..a3430ec
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/MessageTypeFilter.java
@@ -0,0 +1,54 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets of a specific type of Message (e.g. CHAT).
+ * 
+ * @see org.jivesoftware.smack.packet.Message.Type
+ * @author Ward Harold
+ */
+public class MessageTypeFilter implements PacketFilter {
+
+    private final Message.Type type;
+
+    /**
+     * Creates a new message type filter using the specified message type.
+     * 
+     * @param type the message type.
+     */
+    public MessageTypeFilter(Message.Type type) {
+        this.type = type;
+    }
+
+    public boolean accept(Packet packet) {
+        if (!(packet instanceof Message)) {
+            return false;
+        }
+        else {
+            return ((Message) packet).getType().equals(this.type);
+        }
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/filter/NotFilter.java b/src/org/jivesoftware/smack/filter/NotFilter.java
new file mode 100644
index 0000000..59537d0
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/NotFilter.java
@@ -0,0 +1,50 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Implements the logical NOT operation on a packet filter. In other words, packets
+ * pass this filter if they do not pass the supplied filter.
+ *
+ * @author Matt Tucker
+ */
+public class NotFilter implements PacketFilter {
+
+    private PacketFilter filter;
+
+    /**
+     * Creates a NOT filter using the specified filter.
+     *
+     * @param filter the filter.
+     */
+    public NotFilter(PacketFilter filter) {
+        if (filter == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        this.filter = filter;
+    }
+
+    public boolean accept(Packet packet) {
+        return !filter.accept(packet);
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/OrFilter.java b/src/org/jivesoftware/smack/filter/OrFilter.java
new file mode 100644
index 0000000..4c34fd0
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/OrFilter.java
@@ -0,0 +1,103 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Implements the logical OR operation over two or more packet filters. In
+ * other words, packets pass this filter if they pass <b>any</b> of the filters.
+ *
+ * @author Matt Tucker
+ */
+public class OrFilter implements PacketFilter {
+
+    /**
+     * The current number of elements in the filter.
+     */
+    private int size;
+
+    /**
+     * The list of filters.
+     */
+    private PacketFilter [] filters;
+
+    /**
+     * Creates an empty OR filter. Filters should be added using the
+     * {@link #addFilter(PacketFilter)} method.
+     */
+    public OrFilter() {
+        size = 0;
+        filters = new PacketFilter[3];
+    }
+
+    /**
+     * Creates an OR filter using the two specified filters.
+     *
+     * @param filter1 the first packet filter.
+     * @param filter2 the second packet filter.
+     */
+    public OrFilter(PacketFilter filter1, PacketFilter filter2) {
+        if (filter1 == null || filter2 == null) {
+            throw new IllegalArgumentException("Parameters cannot be null.");
+        }
+        size = 2;
+        filters = new PacketFilter[2];
+        filters[0] = filter1;
+        filters[1] = filter2;
+    }
+
+    /**
+     * Adds a filter to the filter list for the OR operation. A packet
+     * will pass the filter if any filter in the list accepts it.
+     *
+     * @param filter a filter to add to the filter list.
+     */
+    public void addFilter(PacketFilter filter) {
+        if (filter == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        // If there is no more room left in the filters array, expand it.
+        if (size == filters.length) {
+            PacketFilter [] newFilters = new PacketFilter[filters.length+2];
+            for (int i=0; i<filters.length; i++) {
+                newFilters[i] = filters[i];
+            }
+            filters = newFilters;
+        }
+        // Add the new filter to the array.
+        filters[size] = filter;
+        size++;
+    }
+
+    public boolean accept(Packet packet) {
+        for (int i=0; i<size; i++) {
+            if (filters[i].accept(packet)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    public String toString() {
+        return filters.toString();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/filter/PacketExtensionFilter.java b/src/org/jivesoftware/smack/filter/PacketExtensionFilter.java
new file mode 100644
index 0000000..3cdc09c
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/PacketExtensionFilter.java
@@ -0,0 +1,61 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets with a particular type of packet extension.
+ *
+ * @author Matt Tucker
+ */
+public class PacketExtensionFilter implements PacketFilter {
+
+    private String elementName;
+    private String namespace;
+
+    /**
+     * Creates a new packet extension filter. Packets will pass the filter if
+     * they have a packet extension that matches the specified element name
+     * and namespace.
+     *
+     * @param elementName the XML element name of the packet extension.
+     * @param namespace the XML namespace of the packet extension.
+     */
+    public PacketExtensionFilter(String elementName, String namespace) {
+        this.elementName = elementName;
+        this.namespace = namespace;
+    }
+
+    /**
+     * Creates a new packet extension filter. Packets will pass the filter if they have a packet
+     * extension that matches the specified namespace.
+     *
+     * @param namespace the XML namespace of the packet extension.
+     */
+    public PacketExtensionFilter(String namespace) {
+        this(null, namespace);
+    }
+
+    public boolean accept(Packet packet) {
+        return packet.getExtension(elementName, namespace) != null;
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/PacketFilter.java b/src/org/jivesoftware/smack/filter/PacketFilter.java
new file mode 100644
index 0000000..634e68e
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/PacketFilter.java
@@ -0,0 +1,63 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Defines a way to filter packets for particular attributes. Packet filters are
+ * used when constructing packet listeners or collectors -- the filter defines
+ * what packets match the criteria of the collector or listener for further
+ * packet processing.<p>
+ *
+ * Several pre-defined filters are defined. These filters can be logically combined
+ * for more complex packet filtering by using the
+ * {@link org.jivesoftware.smack.filter.AndFilter AndFilter} and
+ * {@link org.jivesoftware.smack.filter.OrFilter OrFilter} filters. It's also possible
+ * to define your own filters by implementing this interface. The code example below
+ * creates a trivial filter for packets with a specific ID.
+ *
+ * <pre>
+ * // Use an anonymous inner class to define a packet filter that returns
+ * // all packets that have a packet ID of "RS145".
+ * PacketFilter myFilter = new PacketFilter() {
+ *     public boolean accept(Packet packet) {
+ *         return "RS145".equals(packet.getPacketID());
+ *     }
+ * };
+ * // Create a new packet collector using the filter we created.
+ * PacketCollector myCollector = packetReader.createPacketCollector(myFilter);
+ * </pre>
+ *
+ * @see org.jivesoftware.smack.PacketCollector
+ * @see org.jivesoftware.smack.PacketListener
+ * @author Matt Tucker
+ */
+public interface PacketFilter {
+
+    /**
+     * Tests whether or not the specified packet should pass the filter.
+     *
+     * @param packet the packet to test.
+     * @return true if and only if <tt>packet</tt> passes the filter.
+     */
+    public boolean accept(Packet packet);
+}
diff --git a/src/org/jivesoftware/smack/filter/PacketIDFilter.java b/src/org/jivesoftware/smack/filter/PacketIDFilter.java
new file mode 100644
index 0000000..8d68201
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/PacketIDFilter.java
@@ -0,0 +1,53 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets with a particular packet ID.
+ *
+ * @author Matt Tucker
+ */
+public class PacketIDFilter implements PacketFilter {
+
+    private String packetID;
+
+    /**
+     * Creates a new packet ID filter using the specified packet ID.
+     *
+     * @param packetID the packet ID to filter for.
+     */
+    public PacketIDFilter(String packetID) {
+        if (packetID == null) {
+            throw new IllegalArgumentException("Packet ID cannot be null.");
+        }
+        this.packetID = packetID;
+    }
+
+    public boolean accept(Packet packet) {
+        return packetID.equals(packet.getPacketID());
+    }
+
+    public String toString() {
+        return "PacketIDFilter by id: " + packetID;
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/PacketTypeFilter.java b/src/org/jivesoftware/smack/filter/PacketTypeFilter.java
new file mode 100644
index 0000000..19c573f
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/PacketTypeFilter.java
@@ -0,0 +1,61 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets of a particular type. The type is given as a Class object, so
+ * example types would:
+ * <ul>
+ *      <li><tt>Message.class</tt>
+ *      <li><tt>IQ.class</tt>
+ *      <li><tt>Presence.class</tt>
+ * </ul>
+ *
+ * @author Matt Tucker
+ */
+public class PacketTypeFilter implements PacketFilter {
+
+    Class<? extends Packet> packetType;
+
+    /**
+     * Creates a new packet type filter that will filter for packets that are the
+     * same type as <tt>packetType</tt>.
+     *
+     * @param packetType the Class type.
+     */
+    public PacketTypeFilter(Class<? extends Packet> packetType) {
+        // Ensure the packet type is a sub-class of Packet.
+        if (!Packet.class.isAssignableFrom(packetType)) {
+            throw new IllegalArgumentException("Packet type must be a sub-class of Packet.");
+        }
+        this.packetType = packetType;
+    }
+
+    public boolean accept(Packet packet) {
+        return packetType.isInstance(packet);
+    }
+
+    public String toString() {
+        return "PacketTypeFilter: " + packetType.getName();
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/ThreadFilter.java b/src/org/jivesoftware/smack/filter/ThreadFilter.java
new file mode 100644
index 0000000..8ba8b2e
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/ThreadFilter.java
@@ -0,0 +1,50 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Message;
+
+/**
+ * Filters for message packets with a particular thread value.
+ *
+ * @author Matt Tucker
+ */
+public class ThreadFilter implements PacketFilter {
+
+    private String thread;
+
+    /**
+     * Creates a new thread filter using the specified thread value.
+     *
+     * @param thread the thread value to filter for.
+     */
+    public ThreadFilter(String thread) {
+        if (thread == null) {
+            throw new IllegalArgumentException("Thread cannot be null.");
+        }
+        this.thread = thread;
+    }
+
+    public boolean accept(Packet packet) {
+        return packet instanceof Message && thread.equals(((Message) packet).getThread());
+    }
+}
diff --git a/src/org/jivesoftware/smack/filter/ToContainsFilter.java b/src/org/jivesoftware/smack/filter/ToContainsFilter.java
new file mode 100644
index 0000000..8069fcc
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/ToContainsFilter.java
@@ -0,0 +1,55 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.filter;
+
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Filters for packets where the "to" field contains a specified value. For example,
+ * the filter could be used to listen for all packets sent to a group chat nickname.
+ *
+ * @author Matt Tucker
+ */
+public class ToContainsFilter implements PacketFilter {
+
+    private String to;
+
+    /**
+     * Creates a "to" contains filter using the "to" field part.
+     *
+     * @param to the to field value the packet must contain.
+     */
+    public ToContainsFilter(String to) {
+        if (to == null) {
+            throw new IllegalArgumentException("Parameter cannot be null.");
+        }
+        this.to = to.toLowerCase();
+    }
+
+    public boolean accept(Packet packet) {
+        if (packet.getTo() == null) {
+            return false;
+        }
+        else {
+            return packet.getTo().toLowerCase().indexOf(to) != -1;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/filter/package.html b/src/org/jivesoftware/smack/filter/package.html
new file mode 100644
index 0000000..8b3fe80
--- /dev/null
+++ b/src/org/jivesoftware/smack/filter/package.html
@@ -0,0 +1 @@
+<body>Allows {@link org.jivesoftware.smack.PacketCollector} and {@link org.jivesoftware.smack.PacketListener} instances to filter for packets with particular attributes.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/package.html b/src/org/jivesoftware/smack/package.html
new file mode 100644
index 0000000..2758d78
--- /dev/null
+++ b/src/org/jivesoftware/smack/package.html
@@ -0,0 +1 @@
+<body>Core classes of the Smack API.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/packet/Authentication.java b/src/org/jivesoftware/smack/packet/Authentication.java
new file mode 100644
index 0000000..a47c079
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Authentication.java
@@ -0,0 +1,186 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * Authentication packet, which can be used to login to a XMPP server as well
+ * as discover login information from the server.
+ */
+public class Authentication extends IQ {
+
+    private String username = null;
+    private String password = null;
+    private String digest = null;
+    private String resource = null;
+
+    /**
+     * Create a new authentication packet. By default, the packet will be in
+     * "set" mode in order to perform an actual authentication with the server.
+     * In order to send a "get" request to get the available authentication
+     * modes back from the server, change the type of the IQ packet to "get":
+     * <p/>
+     * <p><tt>setType(IQ.Type.GET);</tt>
+     */
+    public Authentication() {
+        setType(IQ.Type.SET);
+    }
+
+    /**
+     * Returns the username, or <tt>null</tt> if the username hasn't been sent.
+     *
+     * @return the username.
+     */
+    public String getUsername() {
+        return username;
+    }
+
+    /**
+     * Sets the username.
+     *
+     * @param username the username.
+     */
+    public void setUsername(String username) {
+        this.username = username;
+    }
+
+    /**
+     * Returns the plain text password or <tt>null</tt> if the password hasn't
+     * been set.
+     *
+     * @return the password.
+     */
+    public String getPassword() {
+        return password;
+    }
+
+    /**
+     * Sets the plain text password.
+     *
+     * @param password the password.
+     */
+    public void setPassword(String password) {
+        this.password = password;
+    }
+
+    /**
+     * Returns the password digest or <tt>null</tt> if the digest hasn't
+     * been set. Password digests offer a more secure alternative for
+     * authentication compared to plain text. The digest is the hex-encoded
+     * SHA-1 hash of the connection ID plus the user's password. If the
+     * digest and password are set, digest authentication will be used. If
+     * only one value is set, the respective authentication mode will be used.
+     *
+     * @return the digest of the user's password.
+     */
+    public String getDigest() {
+        return digest;
+    }
+
+    /**
+     * Sets the digest value using a connection ID and password. Password
+     * digests offer a more secure alternative for authentication compared to
+     * plain text. The digest is the hex-encoded SHA-1 hash of the connection ID
+     * plus the user's password. If the digest and password are set, digest
+     * authentication will be used. If only one value is set, the respective
+     * authentication mode will be used.
+     *
+     * @param connectionID the connection ID.
+     * @param password     the password.
+     * @see org.jivesoftware.smack.Connection#getConnectionID()
+     */
+    public void setDigest(String connectionID, String password) {
+        this.digest = StringUtils.hash(connectionID + password);
+    }
+
+    /**
+     * Sets the digest value directly. Password digests offer a more secure
+     * alternative for authentication compared to plain text. The digest is
+     * the hex-encoded SHA-1 hash of the connection ID plus the user's password.
+     * If the digest and password are set, digest authentication will be used.
+     * If only one value is set, the respective authentication mode will be used.
+     *
+     * @param digest the digest, which is the SHA-1 hash of the connection ID
+     *               the user's password, encoded as hex.
+     * @see org.jivesoftware.smack.Connection#getConnectionID()
+     */
+    public void setDigest(String digest) {
+        this.digest = digest;
+    }
+
+    /**
+     * Returns the resource or <tt>null</tt> if the resource hasn't been set.
+     *
+     * @return the resource.
+     */
+    public String getResource() {
+        return resource;
+    }
+
+    /**
+     * Sets the resource.
+     *
+     * @param resource the resource.
+     */
+    public void setResource(String resource) {
+        this.resource = resource;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:auth\">");
+        if (username != null) {
+            if (username.equals("")) {
+                buf.append("<username/>");
+            }
+            else {
+                buf.append("<username>").append(username).append("</username>");
+            }
+        }
+        if (digest != null) {
+            if (digest.equals("")) {
+                buf.append("<digest/>");
+            }
+            else {
+                buf.append("<digest>").append(digest).append("</digest>");
+            }
+        }
+        if (password != null && digest == null) {
+            if (password.equals("")) {
+                buf.append("<password/>");
+            }
+            else {
+                buf.append("<password>").append(StringUtils.escapeForXML(password)).append("</password>");
+            }
+        }
+        if (resource != null) {
+            if (resource.equals("")) {
+                buf.append("<resource/>");
+            }
+            else {
+                buf.append("<resource>").append(resource).append("</resource>");
+            }
+        }
+        buf.append("</query>");
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/Bind.java b/src/org/jivesoftware/smack/packet/Bind.java
new file mode 100644
index 0000000..07cd193
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Bind.java
@@ -0,0 +1,71 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+/**
+ * IQ packet used by Smack to bind a resource and to obtain the jid assigned by the server.
+ * There are two ways to bind a resource. One is simply sending an empty Bind packet where the
+ * server will assign a new resource for this connection. The other option is to set a desired
+ * resource but the server may return a modified version of the sent resource.<p>
+ *
+ * For more information refer to the following
+ * <a href=http://www.xmpp.org/specs/rfc3920.html#bind>link</a>. 
+ *
+ * @author Gaston Dombiak
+ */
+public class Bind extends IQ {
+
+    private String resource = null;
+    private String jid = null;
+
+    public Bind() {
+        setType(IQ.Type.SET);
+    }
+
+    public String getResource() {
+        return resource;
+    }
+
+    public void setResource(String resource) {
+        this.resource = resource;
+    }
+
+    public String getJid() {
+        return jid;
+    }
+
+    public void setJid(String jid) {
+        this.jid = jid;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<bind xmlns=\"urn:ietf:params:xml:ns:xmpp-bind\">");
+        if (resource != null) {
+            buf.append("<resource>").append(resource).append("</resource>");
+        }
+        if (jid != null) {
+            buf.append("<jid>").append(jid).append("</jid>");
+        }
+        buf.append("</bind>");
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/DefaultPacketExtension.java b/src/org/jivesoftware/smack/packet/DefaultPacketExtension.java
new file mode 100644
index 0000000..6cc7934
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/DefaultPacketExtension.java
@@ -0,0 +1,133 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import java.util.*;
+
+/**
+ * Default implementation of the PacketExtension interface. Unless a PacketExtensionProvider
+ * is registered with {@link org.jivesoftware.smack.provider.ProviderManager ProviderManager},
+ * instances of this class will be returned when getting packet extensions.<p>
+ *
+ * This class provides a very simple representation of an XML sub-document. Each element
+ * is a key in a Map with its CDATA being the value. For example, given the following
+ * XML sub-document:
+ *
+ * <pre>
+ * &lt;foo xmlns="http://bar.com"&gt;
+ *     &lt;color&gt;blue&lt;/color&gt;
+ *     &lt;food&gt;pizza&lt;/food&gt;
+ * &lt;/foo&gt;</pre>
+ *
+ * In this case, getValue("color") would return "blue", and getValue("food") would
+ * return "pizza". This parsing mechanism mechanism is very simplistic and will not work
+ * as desired in all cases (for example, if some of the elements have attributes. In those
+ * cases, a custom PacketExtensionProvider should be used.
+ *
+ * @author Matt Tucker
+ */
+public class DefaultPacketExtension implements PacketExtension {
+
+    private String elementName;
+    private String namespace;
+    private Map<String,String> map;
+
+    /**
+     * Creates a new generic packet extension.
+     *
+     * @param elementName the name of the element of the XML sub-document.
+     * @param namespace the namespace of the element.
+     */
+    public DefaultPacketExtension(String elementName, String namespace) {
+        this.elementName = elementName;
+        this.namespace = namespace;
+    }
+
+     /**
+     * Returns the XML element name of the extension sub-packet root element.
+     *
+     * @return the XML element name of the packet extension.
+     */
+    public String getElementName() {
+        return elementName;
+    }
+
+    /**
+     * Returns the XML namespace of the extension sub-packet root element.
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return namespace;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(elementName).append(" xmlns=\"").append(namespace).append("\">");
+        for (String name : getNames()) {
+            String value = getValue(name);
+            buf.append("<").append(name).append(">");
+            buf.append(value);
+            buf.append("</").append(name).append(">");
+        }
+        buf.append("</").append(elementName).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Returns an unmodifiable collection of the names that can be used to get
+     * values of the packet extension.
+     *
+     * @return the names.
+     */
+    public synchronized Collection<String> getNames() {
+        if (map == null) {
+            return Collections.emptySet();
+        }
+        return Collections.unmodifiableSet(new HashMap<String,String>(map).keySet());
+    }
+
+    /**
+     * Returns a packet extension value given a name.
+     *
+     * @param name the name.
+     * @return the value.
+     */
+    public synchronized String getValue(String name) {
+        if (map == null) {
+            return null;
+        }
+        return map.get(name);
+    }
+
+    /**
+     * Sets a packet extension value using the given name.
+     *
+     * @param name the name.
+     * @param value the value.
+     */
+    public synchronized void setValue(String name, String value) {
+        if (map == null) {
+            map = new HashMap<String,String>();
+        }
+        map.put(name, value);
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/packet/IQ.java b/src/org/jivesoftware/smack/packet/IQ.java
new file mode 100644
index 0000000..8e1f7d4
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/IQ.java
@@ -0,0 +1,244 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * The base IQ (Info/Query) packet. IQ packets are used to get and set information
+ * on the server, including authentication, roster operations, and creating
+ * accounts. Each IQ packet has a specific type that indicates what type of action
+ * is being taken: "get", "set", "result", or "error".<p>
+ *
+ * IQ packets can contain a single child element that exists in a specific XML
+ * namespace. The combination of the element name and namespace determines what
+ * type of IQ packet it is. Some example IQ subpacket snippets:<ul>
+ *
+ *  <li>&lt;query xmlns="jabber:iq:auth"&gt; -- an authentication IQ.
+ *  <li>&lt;query xmlns="jabber:iq:private"&gt; -- a private storage IQ.
+ *  <li>&lt;pubsub xmlns="http://jabber.org/protocol/pubsub"&gt; -- a pubsub IQ.
+ * </ul>
+ *
+ * @author Matt Tucker
+ */
+public abstract class IQ extends Packet {
+
+    private Type type = Type.GET;
+
+    public IQ() {
+        super();
+    }
+
+    public IQ(IQ iq) {
+        super(iq);
+        type = iq.getType();
+    }
+    /**
+     * Returns the type of the IQ packet.
+     *
+     * @return the type of the IQ packet.
+     */
+    public Type getType() {
+        return type;
+    }
+
+    /**
+     * Sets the type of the IQ packet.
+     *
+     * @param type the type of the IQ packet.
+     */
+    public void setType(Type type) {
+        if (type == null) {
+            this.type = Type.GET;
+        }
+        else {
+            this.type = type;
+        }
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<iq ");
+        if (getPacketID() != null) {
+            buf.append("id=\"" + getPacketID() + "\" ");
+        }
+        if (getTo() != null) {
+            buf.append("to=\"").append(StringUtils.escapeForXML(getTo())).append("\" ");
+        }
+        if (getFrom() != null) {
+            buf.append("from=\"").append(StringUtils.escapeForXML(getFrom())).append("\" ");
+        }
+        if (type == null) {
+            buf.append("type=\"get\">");
+        }
+        else {
+            buf.append("type=\"").append(getType()).append("\">");
+        }
+        // Add the query section if there is one.
+        String queryXML = getChildElementXML();
+        if (queryXML != null) {
+            buf.append(queryXML);
+        }
+        // Add the error sub-packet, if there is one.
+        XMPPError error = getError();
+        if (error != null) {
+            buf.append(error.toXML());
+        }
+        buf.append("</iq>");
+        return buf.toString();
+    }
+
+    /**
+     * Returns the sub-element XML section of the IQ packet, or <tt>null</tt> if there
+     * isn't one. Packet extensions <b>must</b> be included, if any are defined.<p>
+     *
+     * Extensions of this class must override this method.
+     *
+     * @return the child element section of the IQ XML.
+     */
+    public abstract String getChildElementXML();
+
+    /**
+     * Convenience method to create a new empty {@link Type#RESULT IQ.Type.RESULT}
+     * IQ based on a {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET}
+     * IQ. The new packet will be initialized with:<ul>
+     *      <li>The sender set to the recipient of the originating IQ.
+     *      <li>The recipient set to the sender of the originating IQ.
+     *      <li>The type set to {@link Type#RESULT IQ.Type.RESULT}.
+     *      <li>The id set to the id of the originating IQ.
+     *      <li>No child element of the IQ element.
+     * </ul>
+     *
+     * @param iq the {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET} IQ packet.
+     * @throws IllegalArgumentException if the IQ packet does not have a type of
+     *      {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET}.
+     * @return a new {@link Type#RESULT IQ.Type.RESULT} IQ based on the originating IQ.
+     */
+    public static IQ createResultIQ(final IQ request) {
+        if (!(request.getType() == Type.GET || request.getType() == Type.SET)) {
+            throw new IllegalArgumentException(
+                    "IQ must be of type 'set' or 'get'. Original IQ: " + request.toXML());
+        }
+        final IQ result = new IQ() {
+            public String getChildElementXML() {
+                return null;
+            }
+        };
+        result.setType(Type.RESULT);
+        result.setPacketID(request.getPacketID());
+        result.setFrom(request.getTo());
+        result.setTo(request.getFrom());
+        return result;
+    }
+
+    /**
+     * Convenience method to create a new {@link Type#ERROR IQ.Type.ERROR} IQ
+     * based on a {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET}
+     * IQ. The new packet will be initialized with:<ul>
+     *      <li>The sender set to the recipient of the originating IQ.
+     *      <li>The recipient set to the sender of the originating IQ.
+     *      <li>The type set to {@link Type#ERROR IQ.Type.ERROR}.
+     *      <li>The id set to the id of the originating IQ.
+     *      <li>The child element contained in the associated originating IQ.
+     *      <li>The provided {@link XMPPError XMPPError}.
+     * </ul>
+     *
+     * @param iq the {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET} IQ packet.
+     * @param error the error to associate with the created IQ packet.
+     * @throws IllegalArgumentException if the IQ packet does not have a type of
+     *      {@link Type#GET IQ.Type.GET} or {@link Type#SET IQ.Type.SET}.
+     * @return a new {@link Type#ERROR IQ.Type.ERROR} IQ based on the originating IQ.
+     */
+    public static IQ createErrorResponse(final IQ request, final XMPPError error) {
+        if (!(request.getType() == Type.GET || request.getType() == Type.SET)) {
+            throw new IllegalArgumentException(
+                    "IQ must be of type 'set' or 'get'. Original IQ: " + request.toXML());
+        }
+        final IQ result = new IQ() {
+            public String getChildElementXML() {
+                return request.getChildElementXML();
+            }
+        };
+        result.setType(Type.ERROR);
+        result.setPacketID(request.getPacketID());
+        result.setFrom(request.getTo());
+        result.setTo(request.getFrom());
+        result.setError(error);
+        return result;
+    }
+
+    /**
+     * A class to represent the type of the IQ packet. The types are:
+     *
+     * <ul>
+     *      <li>IQ.Type.GET
+     *      <li>IQ.Type.SET
+     *      <li>IQ.Type.RESULT
+     *      <li>IQ.Type.ERROR
+     * </ul>
+     */
+    public static class Type {
+
+        public static final Type GET = new Type("get");
+        public static final Type SET = new Type("set");
+        public static final Type RESULT = new Type("result");
+        public static final Type ERROR = new Type("error");
+
+        /**
+         * Converts a String into the corresponding types. Valid String values
+         * that can be converted to types are: "get", "set", "result", and "error".
+         *
+         * @param type the String value to covert.
+         * @return the corresponding Type.
+         */
+        public static Type fromString(String type) {
+            if (type == null) {
+                return null;
+            }
+            type = type.toLowerCase();
+            if (GET.toString().equals(type)) {
+                return GET;
+            }
+            else if (SET.toString().equals(type)) {
+                return SET;
+            }
+            else if (ERROR.toString().equals(type)) {
+                return ERROR;
+            }
+            else if (RESULT.toString().equals(type)) {
+                return RESULT;
+            }
+            else {
+                return null;
+            }
+        }
+
+        private String value;
+
+        private Type(String value) {
+            this.value = value;
+        }
+
+        public String toString() {
+            return value;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/Message.java b/src/org/jivesoftware/smack/packet/Message.java
new file mode 100644
index 0000000..d28a9f4
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Message.java
@@ -0,0 +1,672 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.*;
+
+/**
+ * Represents XMPP message packets. A message can be one of several types:
+ *
+ * <ul>
+ *      <li>Message.Type.NORMAL -- (Default) a normal text message used in email like interface.
+ *      <li>Message.Type.CHAT -- a typically short text message used in line-by-line chat interfaces.
+ *      <li>Message.Type.GROUP_CHAT -- a chat message sent to a groupchat server for group chats.
+ *      <li>Message.Type.HEADLINE -- a text message to be displayed in scrolling marquee displays.
+ *      <li>Message.Type.ERROR -- indicates a messaging error.
+ * </ul>
+ *
+ * For each message type, different message fields are typically used as follows:
+ * <p>
+ * <table border="1">
+ * <tr><td>&nbsp;</td><td colspan="5"><b>Message type</b></td></tr>
+ * <tr><td><i>Field</i></td><td><b>Normal</b></td><td><b>Chat</b></td><td><b>Group Chat</b></td><td><b>Headline</b></td><td><b>XMPPError</b></td></tr>
+ * <tr><td><i>subject</i></td> <td>SHOULD</td><td>SHOULD NOT</td><td>SHOULD NOT</td><td>SHOULD NOT</td><td>SHOULD NOT</td></tr>
+ * <tr><td><i>thread</i></td>  <td>OPTIONAL</td><td>SHOULD</td><td>OPTIONAL</td><td>OPTIONAL</td><td>SHOULD NOT</td></tr>
+ * <tr><td><i>body</i></td>    <td>SHOULD</td><td>SHOULD</td><td>SHOULD</td><td>SHOULD</td><td>SHOULD NOT</td></tr>
+ * <tr><td><i>error</i></td>   <td>MUST NOT</td><td>MUST NOT</td><td>MUST NOT</td><td>MUST NOT</td><td>MUST</td></tr>
+ * </table>
+ *
+ * @author Matt Tucker
+ */
+public class Message extends Packet {
+
+    private Type type = Type.normal;
+    private String thread = null;
+    private String language;
+
+    private final Set<Subject> subjects = new HashSet<Subject>();
+    private final Set<Body> bodies = new HashSet<Body>();
+
+    /**
+     * Creates a new, "normal" message.
+     */
+    public Message() {
+    }
+
+    /**
+     * Creates a new "normal" message to the specified recipient.
+     *
+     * @param to the recipient of the message.
+     */
+    public Message(String to) {
+        setTo(to);
+    }
+
+    /**
+     * Creates a new message of the specified type to a recipient.
+     *
+     * @param to the user to send the message to.
+     * @param type the message type.
+     */
+    public Message(String to, Type type) {
+        setTo(to);
+        this.type = type;
+    }
+
+    /**
+     * Returns the type of the message. If no type has been set this method will return {@link
+     * org.jivesoftware.smack.packet.Message.Type#normal}.
+     *
+     * @return the type of the message.
+     */
+    public Type getType() {
+        return type;
+    }
+
+    /**
+     * Sets the type of the message.
+     *
+     * @param type the type of the message.
+     * @throws IllegalArgumentException if null is passed in as the type
+     */
+    public void setType(Type type) {
+        if (type == null) {
+            throw new IllegalArgumentException("Type cannot be null.");
+        }
+        this.type = type;
+    }
+
+    /**
+     * Returns the default subject of the message, or null if the subject has not been set.
+     * The subject is a short description of message contents.
+     * <p>
+     * The default subject of a message is the subject that corresponds to the message's language.
+     * (see {@link #getLanguage()}) or if no language is set to the applications default
+     * language (see {@link Packet#getDefaultLanguage()}).
+     *
+     * @return the subject of the message.
+     */
+    public String getSubject() {
+        return getSubject(null);
+    }
+    
+    /**
+     * Returns the subject corresponding to the language. If the language is null, the method result
+     * will be the same as {@link #getSubject()}. Null will be returned if the language does not have
+     * a corresponding subject.
+     *
+     * @param language the language of the subject to return.
+     * @return the subject related to the passed in language.
+     */
+    public String getSubject(String language) {
+        Subject subject = getMessageSubject(language);
+        return subject == null ? null : subject.subject;
+    }
+    
+    private Subject getMessageSubject(String language) {
+        language = determineLanguage(language);
+        for (Subject subject : subjects) {
+            if (language.equals(subject.language)) {
+                return subject;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns a set of all subjects in this Message, including the default message subject accessible
+     * from {@link #getSubject()}.
+     *
+     * @return a collection of all subjects in this message.
+     */
+    public Collection<Subject> getSubjects() {
+        return Collections.unmodifiableCollection(subjects);
+    }
+
+    /**
+     * Sets the subject of the message. The subject is a short description of
+     * message contents.
+     *
+     * @param subject the subject of the message.
+     */
+    public void setSubject(String subject) {
+        if (subject == null) {
+            removeSubject(""); // use empty string because #removeSubject(null) is ambiguous 
+            return;
+        }
+        addSubject(null, subject);
+    }
+
+    /**
+     * Adds a subject with a corresponding language.
+     *
+     * @param language the language of the subject being added.
+     * @param subject the subject being added to the message.
+     * @return the new {@link org.jivesoftware.smack.packet.Message.Subject}
+     * @throws NullPointerException if the subject is null, a null pointer exception is thrown
+     */
+    public Subject addSubject(String language, String subject) {
+        language = determineLanguage(language);
+        Subject messageSubject = new Subject(language, subject);
+        subjects.add(messageSubject);
+        return messageSubject;
+    }
+
+    /**
+     * Removes the subject with the given language from the message.
+     *
+     * @param language the language of the subject which is to be removed
+     * @return true if a subject was removed and false if it was not.
+     */
+    public boolean removeSubject(String language) {
+        language = determineLanguage(language);
+        for (Subject subject : subjects) {
+            if (language.equals(subject.language)) {
+                return subjects.remove(subject);
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Removes the subject from the message and returns true if the subject was removed.
+     *
+     * @param subject the subject being removed from the message.
+     * @return true if the subject was successfully removed and false if it was not.
+     */
+    public boolean removeSubject(Subject subject) {
+        return subjects.remove(subject);
+    }
+
+    /**
+     * Returns all the languages being used for the subjects, not including the default subject.
+     *
+     * @return the languages being used for the subjects.
+     */
+    public Collection<String> getSubjectLanguages() {
+        Subject defaultSubject = getMessageSubject(null);
+        List<String> languages = new ArrayList<String>();
+        for (Subject subject : subjects) {
+            if (!subject.equals(defaultSubject)) {
+                languages.add(subject.language);
+            }
+        }
+        return Collections.unmodifiableCollection(languages);
+    }
+
+    /**
+     * Returns the default body of the message, or null if the body has not been set. The body
+     * is the main message contents.
+     * <p>
+     * The default body of a message is the body that corresponds to the message's language.
+     * (see {@link #getLanguage()}) or if no language is set to the applications default
+     * language (see {@link Packet#getDefaultLanguage()}).
+     *
+     * @return the body of the message.
+     */
+    public String getBody() {
+        return getBody(null);
+    }
+
+    /**
+     * Returns the body corresponding to the language. If the language is null, the method result
+     * will be the same as {@link #getBody()}. Null will be returned if the language does not have
+     * a corresponding body.
+     *
+     * @param language the language of the body to return.
+     * @return the body related to the passed in language.
+     * @since 3.0.2
+     */
+    public String getBody(String language) {
+        Body body = getMessageBody(language);
+        return body == null ? null : body.message;
+    }
+    
+    private Body getMessageBody(String language) {
+        language = determineLanguage(language);
+        for (Body body : bodies) {
+            if (language.equals(body.language)) {
+                return body;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns a set of all bodies in this Message, including the default message body accessible
+     * from {@link #getBody()}.
+     *
+     * @return a collection of all bodies in this Message.
+     * @since 3.0.2
+     */
+    public Collection<Body> getBodies() {
+        return Collections.unmodifiableCollection(bodies);
+    }
+
+    /**
+     * Sets the body of the message. The body is the main message contents.
+     *
+     * @param body the body of the message.
+     */
+    public void setBody(String body) {
+        if (body == null) {
+            removeBody(""); // use empty string because #removeBody(null) is ambiguous
+            return;
+        }
+        addBody(null, body);
+    }
+
+    /**
+     * Adds a body with a corresponding language.
+     *
+     * @param language the language of the body being added.
+     * @param body the body being added to the message.
+     * @return the new {@link org.jivesoftware.smack.packet.Message.Body}
+     * @throws NullPointerException if the body is null, a null pointer exception is thrown
+     * @since 3.0.2
+     */
+    public Body addBody(String language, String body) {
+        language = determineLanguage(language);
+        Body messageBody = new Body(language, body);
+        bodies.add(messageBody);
+        return messageBody;
+    }
+
+    /**
+     * Removes the body with the given language from the message.
+     *
+     * @param language the language of the body which is to be removed
+     * @return true if a body was removed and false if it was not.
+     */
+    public boolean removeBody(String language) {
+        language = determineLanguage(language);
+        for (Body body : bodies) {
+            if (language.equals(body.language)) {
+                return bodies.remove(body);
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Removes the body from the message and returns true if the body was removed.
+     *
+     * @param body the body being removed from the message.
+     * @return true if the body was successfully removed and false if it was not.
+     * @since 3.0.2
+     */
+    public boolean removeBody(Body body) {
+        return bodies.remove(body);
+    }
+
+    /**
+     * Returns all the languages being used for the bodies, not including the default body.
+     *
+     * @return the languages being used for the bodies.
+     * @since 3.0.2
+     */
+    public Collection<String> getBodyLanguages() {
+        Body defaultBody = getMessageBody(null);
+        List<String> languages = new ArrayList<String>();
+        for (Body body : bodies) {
+            if (!body.equals(defaultBody)) {
+                languages.add(body.language);
+            }
+        }
+        return Collections.unmodifiableCollection(languages);
+    }
+
+    /**
+     * Returns the thread id of the message, which is a unique identifier for a sequence
+     * of "chat" messages. If no thread id is set, <tt>null</tt> will be returned.
+     *
+     * @return the thread id of the message, or <tt>null</tt> if it doesn't exist.
+     */
+    public String getThread() {
+        return thread;
+    }
+
+    /**
+     * Sets the thread id of the message, which is a unique identifier for a sequence
+     * of "chat" messages.
+     *
+     * @param thread the thread id of the message.
+     */
+    public void setThread(String thread) {
+        this.thread = thread;
+    }
+
+    /**
+     * Returns the xml:lang of this Message.
+     *
+     * @return the xml:lang of this Message.
+     * @since 3.0.2
+     */
+    public String getLanguage() {
+        return language;
+    }
+
+    /**
+     * Sets the xml:lang of this Message.
+     *
+     * @param language the xml:lang of this Message.
+     * @since 3.0.2
+     */
+    public void setLanguage(String language) {
+        this.language = language;
+    }
+
+    private String determineLanguage(String language) {
+        
+        // empty string is passed by #setSubject() and #setBody() and is the same as null
+        language = "".equals(language) ? null : language;
+
+        // if given language is null check if message language is set
+        if (language == null && this.language != null) {
+            return this.language;
+        }
+        else if (language == null) {
+            return getDefaultLanguage();
+        }
+        else {
+            return language;
+        }
+        
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<message");
+        if (getXmlns() != null) {
+            buf.append(" xmlns=\"").append(getXmlns()).append("\"");
+        }
+        if (language != null) {
+            buf.append(" xml:lang=\"").append(getLanguage()).append("\"");
+        }
+        if (getPacketID() != null) {
+            buf.append(" id=\"").append(getPacketID()).append("\"");
+        }
+        if (getTo() != null) {
+            buf.append(" to=\"").append(StringUtils.escapeForXML(getTo())).append("\"");
+        }
+        if (getFrom() != null) {
+            buf.append(" from=\"").append(StringUtils.escapeForXML(getFrom())).append("\"");
+        }
+        if (type != Type.normal) {
+            buf.append(" type=\"").append(type).append("\"");
+        }
+        buf.append(">");
+        // Add the subject in the default language
+        Subject defaultSubject = getMessageSubject(null);
+        if (defaultSubject != null) {
+            buf.append("<subject>").append(StringUtils.escapeForXML(defaultSubject.subject)).append("</subject>");
+        }
+        // Add the subject in other languages
+        for (Subject subject : getSubjects()) {
+            // Skip the default language
+            if(subject.equals(defaultSubject))
+                continue;
+            buf.append("<subject xml:lang=\"").append(subject.language).append("\">");
+            buf.append(StringUtils.escapeForXML(subject.subject));
+            buf.append("</subject>");
+        }
+        // Add the body in the default language
+        Body defaultBody = getMessageBody(null);
+        if (defaultBody != null) {
+            buf.append("<body>").append(StringUtils.escapeForXML(defaultBody.message)).append("</body>");
+        }
+        // Add the bodies in other languages
+        for (Body body : getBodies()) {
+            // Skip the default language
+            if(body.equals(defaultBody))
+                continue;
+            buf.append("<body xml:lang=\"").append(body.getLanguage()).append("\">");
+            buf.append(StringUtils.escapeForXML(body.getMessage()));
+            buf.append("</body>");
+        }
+        if (thread != null) {
+            buf.append("<thread>").append(thread).append("</thread>");
+        }
+        // Append the error subpacket if the message type is an error.
+        if (type == Type.error) {
+            XMPPError error = getError();
+            if (error != null) {
+                buf.append(error.toXML());
+            }
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</message>");
+        return buf.toString();
+    }
+
+
+    public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+
+        Message message = (Message) o;
+
+        if(!super.equals(message)) { return false; }
+        if (bodies.size() != message.bodies.size() || !bodies.containsAll(message.bodies)) {
+            return false;
+        }
+        if (language != null ? !language.equals(message.language) : message.language != null) {
+            return false;
+        }
+        if (subjects.size() != message.subjects.size() || !subjects.containsAll(message.subjects)) {
+            return false;
+        }
+        if (thread != null ? !thread.equals(message.thread) : message.thread != null) {
+            return false;
+        }
+        return type == message.type;
+
+    }
+
+    public int hashCode() {
+        int result;
+        result = (type != null ? type.hashCode() : 0);
+        result = 31 * result + subjects.hashCode();
+        result = 31 * result + (thread != null ? thread.hashCode() : 0);
+        result = 31 * result + (language != null ? language.hashCode() : 0);
+        result = 31 * result + bodies.hashCode();
+        return result;
+    }
+
+    /**
+     * Represents a message subject, its language and the content of the subject.
+     */
+    public static class Subject {
+
+        private String subject;
+        private String language;
+
+        private Subject(String language, String subject) {
+            if (language == null) {
+                throw new NullPointerException("Language cannot be null.");
+            }
+            if (subject == null) {
+                throw new NullPointerException("Subject cannot be null.");
+            }
+            this.language = language;
+            this.subject = subject;
+        }
+
+        /**
+         * Returns the language of this message subject.
+         *
+         * @return the language of this message subject.
+         */
+        public String getLanguage() {
+            return language;
+        }
+
+        /**
+         * Returns the subject content.
+         *
+         * @return the content of the subject.
+         */
+        public String getSubject() {
+            return subject;
+        }
+
+
+        public int hashCode() {
+            final int prime = 31;
+            int result = 1;
+            result = prime * result + this.language.hashCode();
+            result = prime * result + this.subject.hashCode();
+            return result;
+        }
+
+        public boolean equals(Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (obj == null) {
+                return false;
+            }
+            if (getClass() != obj.getClass()) {
+                return false;
+            }
+            Subject other = (Subject) obj;
+            // simplified comparison because language and subject are always set
+            return this.language.equals(other.language) && this.subject.equals(other.subject);
+        }
+        
+    }
+
+    /**
+     * Represents a message body, its language and the content of the message.
+     */
+    public static class Body {
+
+        private String message;
+        private String language;
+
+        private Body(String language, String message) {
+            if (language == null) {
+                throw new NullPointerException("Language cannot be null.");
+            }
+            if (message == null) {
+                throw new NullPointerException("Message cannot be null.");
+            }
+            this.language = language;
+            this.message = message;
+        }
+
+        /**
+         * Returns the language of this message body.
+         *
+         * @return the language of this message body.
+         */
+        public String getLanguage() {
+            return language;
+        }
+
+        /**
+         * Returns the message content.
+         *
+         * @return the content of the message.
+         */
+        public String getMessage() {
+            return message;
+        }
+
+        public int hashCode() {
+            final int prime = 31;
+            int result = 1;
+            result = prime * result + this.language.hashCode();
+            result = prime * result + this.message.hashCode();
+            return result;
+        }
+
+        public boolean equals(Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (obj == null) {
+                return false;
+            }
+            if (getClass() != obj.getClass()) {
+                return false;
+            }
+            Body other = (Body) obj;
+            // simplified comparison because language and message are always set
+            return this.language.equals(other.language) && this.message.equals(other.message);
+        }
+        
+    }
+
+    /**
+     * Represents the type of a message.
+     */
+    public enum Type {
+
+        /**
+         * (Default) a normal text message used in email like interface.
+         */
+        normal,
+
+        /**
+         * Typically short text message used in line-by-line chat interfaces.
+         */
+        chat,
+
+        /**
+         * Chat message sent to a groupchat server for group chats.
+         */
+        groupchat,
+
+        /**
+         * Text message to be displayed in scrolling marquee displays.
+         */
+        headline,
+
+        /**
+         * indicates a messaging error.
+         */
+        error;
+
+        public static Type fromString(String name) {
+            try {
+                return Type.valueOf(name);
+            }
+            catch (Exception e) {
+                return normal;
+            }
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/Packet.java b/src/org/jivesoftware/smack/packet/Packet.java
new file mode 100644
index 0000000..3f1185e
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Packet.java
@@ -0,0 +1,509 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import java.io.ByteArrayOutputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.TimeZone;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * Base class for XMPP packets. Every packet has a unique ID (which is automatically
+ * generated, but can be overriden). Optionally, the "to" and "from" fields can be set,
+ * as well as an arbitrary number of properties.
+ *
+ * Properties provide an easy mechanism for clients to share data. Each property has a
+ * String name, and a value that is a Java primitive (int, long, float, double, boolean)
+ * or any Serializable object (a Java object is Serializable when it implements the
+ * Serializable interface).
+ *
+ * @author Matt Tucker
+ */
+public abstract class Packet {
+
+    protected static final String DEFAULT_LANGUAGE =
+            java.util.Locale.getDefault().getLanguage().toLowerCase();
+
+    private static String DEFAULT_XML_NS = null;
+
+    /**
+     * Constant used as packetID to indicate that a packet has no id. To indicate that a packet
+     * has no id set this constant as the packet's id. When the packet is asked for its id the
+     * answer will be <tt>null</tt>.
+     */
+    public static final String ID_NOT_AVAILABLE = "ID_NOT_AVAILABLE";
+    
+    /**
+     * Date format as defined in XEP-0082 - XMPP Date and Time Profiles.
+     * The time zone is set to UTC.
+     * <p>
+     * Date formats are not synchronized. Since multiple threads access the format concurrently,
+     * it must be synchronized externally. 
+     */
+    public static final DateFormat XEP_0082_UTC_FORMAT = new SimpleDateFormat(
+                    "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
+    static {
+        XEP_0082_UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC"));
+    }
+
+
+    /**
+     * A prefix helps to make sure that ID's are unique across mutliple instances.
+     */
+    private static String prefix = StringUtils.randomString(5) + "-";
+
+    /**
+     * Keeps track of the current increment, which is appended to the prefix to
+     * forum a unique ID.
+     */
+    private static long id = 0;
+
+    private String xmlns = DEFAULT_XML_NS;
+
+    /**
+     * Returns the next unique id. Each id made up of a short alphanumeric
+     * prefix along with a unique numeric value.
+     *
+     * @return the next id.
+     */
+    public static synchronized String nextID() {
+        return prefix + Long.toString(id++);
+    }
+
+    public static void setDefaultXmlns(String defaultXmlns) {
+        DEFAULT_XML_NS = defaultXmlns;
+    }
+
+    private String packetID = null;
+    private String to = null;
+    private String from = null;
+    private final List<PacketExtension> packetExtensions
+            = new CopyOnWriteArrayList<PacketExtension>();
+
+    private final Map<String,Object> properties = new HashMap<String, Object>();
+    private XMPPError error = null;
+
+    public Packet() {
+    }
+
+    public Packet(Packet p) {
+        packetID = p.getPacketID();
+        to = p.getTo();
+        from = p.getFrom();
+        xmlns = p.xmlns;
+        error = p.error;
+
+        // Copy extensions
+        for (PacketExtension pe : p.getExtensions()) {
+            addExtension(pe);
+        }
+    }
+
+    /**
+     * Returns the unique ID of the packet. The returned value could be <tt>null</tt> when
+     * ID_NOT_AVAILABLE was set as the packet's id.
+     *
+     * @return the packet's unique ID or <tt>null</tt> if the packet's id is not available.
+     */
+    public String getPacketID() {
+        if (ID_NOT_AVAILABLE.equals(packetID)) {
+            return null;
+        }
+
+        if (packetID == null) {
+            packetID = nextID();
+        }
+        return packetID;
+    }
+
+    /**
+     * Sets the unique ID of the packet. To indicate that a packet has no id
+     * pass the constant ID_NOT_AVAILABLE as the packet's id value.
+     *
+     * @param packetID the unique ID for the packet.
+     */
+    public void setPacketID(String packetID) {
+        this.packetID = packetID;
+    }
+
+    /**
+     * Returns who the packet is being sent "to", or <tt>null</tt> if
+     * the value is not set. The XMPP protocol often makes the "to"
+     * attribute optional, so it does not always need to be set.<p>
+     *
+     * The StringUtils class provides several useful methods for dealing with
+     * XMPP addresses such as parsing the
+     * {@link StringUtils#parseBareAddress(String) bare address},
+     * {@link StringUtils#parseName(String) user name},
+     * {@link StringUtils#parseServer(String) server}, and
+     * {@link StringUtils#parseResource(String) resource}.  
+     *
+     * @return who the packet is being sent to, or <tt>null</tt> if the
+     *      value has not been set.
+     */
+    public String getTo() {
+        return to;
+    }
+
+    /**
+     * Sets who the packet is being sent "to". The XMPP protocol often makes
+     * the "to" attribute optional, so it does not always need to be set.
+     *
+     * @param to who the packet is being sent to.
+     */
+    public void setTo(String to) {
+        this.to = to;
+    }
+
+    /**
+     * Returns who the packet is being sent "from" or <tt>null</tt> if
+     * the value is not set. The XMPP protocol often makes the "from"
+     * attribute optional, so it does not always need to be set.<p>
+     *
+     * The StringUtils class provides several useful methods for dealing with
+     * XMPP addresses such as parsing the
+     * {@link StringUtils#parseBareAddress(String) bare address},
+     * {@link StringUtils#parseName(String) user name},
+     * {@link StringUtils#parseServer(String) server}, and
+     * {@link StringUtils#parseResource(String) resource}.  
+     *
+     * @return who the packet is being sent from, or <tt>null</tt> if the
+     *      value has not been set.
+     */
+    public String getFrom() {
+        return from;
+    }
+
+    /**
+     * Sets who the packet is being sent "from". The XMPP protocol often
+     * makes the "from" attribute optional, so it does not always need to
+     * be set.
+     *
+     * @param from who the packet is being sent to.
+     */
+    public void setFrom(String from) {
+        this.from = from;
+    }
+
+    /**
+     * Returns the error associated with this packet, or <tt>null</tt> if there are
+     * no errors.
+     *
+     * @return the error sub-packet or <tt>null</tt> if there isn't an error.
+     */
+    public XMPPError getError() {
+        return error;
+    }
+
+    /**
+     * Sets the error for this packet.
+     *
+     * @param error the error to associate with this packet.
+     */
+    public void setError(XMPPError error) {
+        this.error = error;
+    }
+
+    /**
+     * Returns an unmodifiable collection of the packet extensions attached to the packet.
+     *
+     * @return the packet extensions.
+     */
+    public synchronized Collection<PacketExtension> getExtensions() {
+        if (packetExtensions == null) {
+            return Collections.emptyList();
+        }
+        return Collections.unmodifiableList(new ArrayList<PacketExtension>(packetExtensions));
+    }
+
+    /**
+     * Returns the first extension of this packet that has the given namespace.
+     *
+     * @param namespace the namespace of the extension that is desired.
+     * @return the packet extension with the given namespace.
+     */
+    public PacketExtension getExtension(String namespace) {
+        return getExtension(null, namespace);
+    }
+
+    /**
+     * Returns the first packet extension that matches the specified element name and
+     * namespace, or <tt>null</tt> if it doesn't exist. If the provided elementName is null
+     * than only the provided namespace is attempted to be matched. Packet extensions are
+     * are arbitrary XML sub-documents in standard XMPP packets. By default, a 
+     * DefaultPacketExtension instance will be returned for each extension. However, 
+     * PacketExtensionProvider instances can be registered with the 
+     * {@link org.jivesoftware.smack.provider.ProviderManager ProviderManager}
+     * class to handle custom parsing. In that case, the type of the Object
+     * will be determined by the provider.
+     *
+     * @param elementName the XML element name of the packet extension. (May be null)
+     * @param namespace the XML element namespace of the packet extension.
+     * @return the extension, or <tt>null</tt> if it doesn't exist.
+     */
+    public PacketExtension getExtension(String elementName, String namespace) {
+        if (namespace == null) {
+            return null;
+        }
+        for (PacketExtension ext : packetExtensions) {
+            if ((elementName == null || elementName.equals(ext.getElementName()))
+                    && namespace.equals(ext.getNamespace()))
+            {
+                return ext;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Adds a packet extension to the packet. Does nothing if extension is null.
+     *
+     * @param extension a packet extension.
+     */
+    public void addExtension(PacketExtension extension) {
+        if (extension == null) return;
+        packetExtensions.add(extension);
+    }
+
+    /**
+     * Adds a collection of packet extensions to the packet. Does nothing if extensions is null.
+     * 
+     * @param extensions a collection of packet extensions
+     */
+    public void addExtensions(Collection<PacketExtension> extensions) {
+        if (extensions == null) return;
+        packetExtensions.addAll(extensions);
+    }
+
+    /**
+     * Removes a packet extension from the packet.
+     *
+     * @param extension the packet extension to remove.
+     */
+    public void removeExtension(PacketExtension extension)  {
+        packetExtensions.remove(extension);
+    }
+
+    /**
+     * Returns the packet property with the specified name or <tt>null</tt> if the
+     * property doesn't exist. Property values that were originally primitives will
+     * be returned as their object equivalent. For example, an int property will be
+     * returned as an Integer, a double as a Double, etc.
+     *
+     * @param name the name of the property.
+     * @return the property, or <tt>null</tt> if the property doesn't exist.
+     */
+    public synchronized Object getProperty(String name) {
+        if (properties == null) {
+            return null;
+        }
+        return properties.get(name);
+    }
+
+    /**
+     * Sets a property with an Object as the value. The value must be Serializable
+     * or an IllegalArgumentException will be thrown.
+     *
+     * @param name the name of the property.
+     * @param value the value of the property.
+     */
+    public synchronized void setProperty(String name, Object value) {
+        if (!(value instanceof Serializable)) {
+            throw new IllegalArgumentException("Value must be serialiazble");
+        }
+        properties.put(name, value);
+    }
+
+    /**
+     * Deletes a property.
+     *
+     * @param name the name of the property to delete.
+     */
+    public synchronized void deleteProperty(String name) {
+        if (properties == null) {
+            return;
+        }
+        properties.remove(name);
+    }
+
+    /**
+     * Returns an unmodifiable collection of all the property names that are set.
+     *
+     * @return all property names.
+     */
+    public synchronized Collection<String> getPropertyNames() {
+        if (properties == null) {
+            return Collections.emptySet();
+        }
+        return Collections.unmodifiableSet(new HashSet<String>(properties.keySet()));
+    }
+
+    /**
+     * Returns the packet as XML. Every concrete extension of Packet must implement
+     * this method. In addition to writing out packet-specific data, every sub-class
+     * should also write out the error and the extensions data if they are defined.
+     *
+     * @return the XML format of the packet as a String.
+     */
+    public abstract String toXML();
+
+    /**
+     * Returns the extension sub-packets (including properties data) as an XML
+     * String, or the Empty String if there are no packet extensions.
+     *
+     * @return the extension sub-packets as XML or the Empty String if there
+     * are no packet extensions.
+     */
+    protected synchronized String getExtensionsXML() {
+        StringBuilder buf = new StringBuilder();
+        // Add in all standard extension sub-packets.
+        for (PacketExtension extension : getExtensions()) {
+            buf.append(extension.toXML());
+        }
+        // Add in packet properties.
+        if (properties != null && !properties.isEmpty()) {
+            buf.append("<properties xmlns=\"http://www.jivesoftware.com/xmlns/xmpp/properties\">");
+            // Loop through all properties and write them out.
+            for (String name : getPropertyNames()) {
+                Object value = getProperty(name);
+                buf.append("<property>");
+                buf.append("<name>").append(StringUtils.escapeForXML(name)).append("</name>");
+                buf.append("<value type=\"");
+                if (value instanceof Integer) {
+                    buf.append("integer\">").append(value).append("</value>");
+                }
+                else if (value instanceof Long) {
+                    buf.append("long\">").append(value).append("</value>");
+                }
+                else if (value instanceof Float) {
+                    buf.append("float\">").append(value).append("</value>");
+                }
+                else if (value instanceof Double) {
+                    buf.append("double\">").append(value).append("</value>");
+                }
+                else if (value instanceof Boolean) {
+                    buf.append("boolean\">").append(value).append("</value>");
+                }
+                else if (value instanceof String) {
+                    buf.append("string\">");
+                    buf.append(StringUtils.escapeForXML((String)value));
+                    buf.append("</value>");
+                }
+                // Otherwise, it's a generic Serializable object. Serialized objects are in
+                // a binary format, which won't work well inside of XML. Therefore, we base-64
+                // encode the binary data before adding it.
+                else {
+                    ByteArrayOutputStream byteStream = null;
+                    ObjectOutputStream out = null;
+                    try {
+                        byteStream = new ByteArrayOutputStream();
+                        out = new ObjectOutputStream(byteStream);
+                        out.writeObject(value);
+                        buf.append("java-object\">");
+                        String encodedVal = StringUtils.encodeBase64(byteStream.toByteArray());
+                        buf.append(encodedVal).append("</value>");
+                    }
+                    catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                    finally {
+                        if (out != null) {
+                            try {
+                                out.close();
+                            }
+                            catch (Exception e) {
+                                // Ignore.
+                            }
+                        }
+                        if (byteStream != null) {
+                            try {
+                                byteStream.close();
+                            }
+                            catch (Exception e) {
+                                // Ignore.
+                            }
+                        }
+                    }
+                }
+                buf.append("</property>");
+            }
+            buf.append("</properties>");
+        }
+        return buf.toString();
+    }
+
+    public String getXmlns() {
+        return this.xmlns;
+    }
+
+    /**
+     * Returns the default language used for all messages containing localized content.
+     * 
+     * @return the default language
+     */
+    public static String getDefaultLanguage() {
+        return DEFAULT_LANGUAGE;
+    }
+
+    public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+
+        Packet packet = (Packet) o;
+
+        if (error != null ? !error.equals(packet.error) : packet.error != null) { return false; }
+        if (from != null ? !from.equals(packet.from) : packet.from != null) { return false; }
+        if (!packetExtensions.equals(packet.packetExtensions)) { return false; }
+        if (packetID != null ? !packetID.equals(packet.packetID) : packet.packetID != null) {
+            return false;
+        }
+        if (properties != null ? !properties.equals(packet.properties)
+                : packet.properties != null) {
+            return false;
+        }
+        if (to != null ? !to.equals(packet.to) : packet.to != null)  { return false; }
+        return !(xmlns != null ? !xmlns.equals(packet.xmlns) : packet.xmlns != null);
+    }
+
+    public int hashCode() {
+        int result;
+        result = (xmlns != null ? xmlns.hashCode() : 0);
+        result = 31 * result + (packetID != null ? packetID.hashCode() : 0);
+        result = 31 * result + (to != null ? to.hashCode() : 0);
+        result = 31 * result + (from != null ? from.hashCode() : 0);
+        result = 31 * result + packetExtensions.hashCode();
+        result = 31 * result + properties.hashCode();
+        result = 31 * result + (error != null ? error.hashCode() : 0);
+        return result;
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/PacketExtension.java b/src/org/jivesoftware/smack/packet/PacketExtension.java
new file mode 100644
index 0000000..d2afbf8
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/PacketExtension.java
@@ -0,0 +1,56 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+/**
+ * Interface to represent packet extensions. A packet extension is an XML subdocument
+ * with a root element name and namespace. Packet extensions are used to provide
+ * extended functionality beyond what is in the base XMPP specification. Examples of
+ * packet extensions include message events, message properties, and extra presence data.
+ * IQ packets cannot contain packet extensions.
+ *
+ * @see DefaultPacketExtension
+ * @see org.jivesoftware.smack.provider.PacketExtensionProvider
+ * @author Matt Tucker
+ */
+public interface PacketExtension {
+
+    /**
+     * Returns the root element name.
+     *
+     * @return the element name.
+     */
+    public String getElementName();
+
+    /**
+     * Returns the root element XML namespace.
+     *
+     * @return the namespace.
+     */
+    public String getNamespace();
+
+    /**
+     * Returns the XML representation of the PacketExtension.
+     *
+     * @return the packet extension as XML.
+     */
+    public String toXML();
+}
diff --git a/src/org/jivesoftware/smack/packet/Presence.java b/src/org/jivesoftware/smack/packet/Presence.java
new file mode 100644
index 0000000..84fcfef
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Presence.java
@@ -0,0 +1,358 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * Represents XMPP presence packets. Every presence packet has a type, which is one of
+ * the following values:
+ * <ul>
+ *      <li>{@link Presence.Type#available available} -- (Default) indicates the user is available to
+ *          receive messages.
+ *      <li>{@link Presence.Type#unavailable unavailable} -- the user is unavailable to receive messages.
+ *      <li>{@link Presence.Type#subscribe subscribe} -- request subscription to recipient's presence.
+ *      <li>{@link Presence.Type#subscribed subscribed} -- grant subscription to sender's presence.
+ *      <li>{@link Presence.Type#unsubscribe unsubscribe} -- request removal of subscription to
+ *          sender's presence.
+ *      <li>{@link Presence.Type#unsubscribed unsubscribed} -- grant removal of subscription to
+ *          sender's presence.
+ *      <li>{@link Presence.Type#error error} -- the presence packet contains an error message.
+ * </ul><p>
+ *
+ * A number of attributes are optional:
+ * <ul>
+ *      <li>Status -- free-form text describing a user's presence (i.e., gone to lunch).
+ *      <li>Priority -- non-negative numerical priority of a sender's resource. The
+ *          highest resource priority is the default recipient of packets not addressed
+ *          to a particular resource.
+ *      <li>Mode -- one of five presence modes: {@link Mode#available available} (the default),
+ *          {@link Mode#chat chat}, {@link Mode#away away}, {@link Mode#xa xa} (extended away), and
+ *          {@link Mode#dnd dnd} (do not disturb).
+ * </ul><p>
+ *
+ * Presence packets are used for two purposes. First, to notify the server of our
+ * the clients current presence status. Second, they are used to subscribe and
+ * unsubscribe users from the roster.
+ *
+ * @see RosterPacket
+ * @author Matt Tucker
+ */
+public class Presence extends Packet {
+
+    private Type type = Type.available;
+    private String status = null;
+    private int priority = Integer.MIN_VALUE;
+    private Mode mode = null;
+    private String language;
+
+    /**
+     * Creates a new presence update. Status, priority, and mode are left un-set.
+     *
+     * @param type the type.
+     */
+    public Presence(Type type) {
+        setType(type);
+    }
+
+    /**
+     * Creates a new presence update with a specified status, priority, and mode.
+     *
+     * @param type the type.
+     * @param status a text message describing the presence update.
+     * @param priority the priority of this presence update.
+     * @param mode the mode type for this presence update.
+     */
+    public Presence(Type type, String status, int priority, Mode mode) {
+        setType(type);
+        setStatus(status);
+        setPriority(priority);
+        setMode(mode);
+    }
+
+    /**
+     * Returns true if the {@link Type presence type} is available (online) and
+     * false if the user is unavailable (offline), or if this is a presence packet
+     * involved in a subscription operation. This is a convenience method
+     * equivalent to <tt>getType() == Presence.Type.available</tt>. Note that even
+     * when the user is available, their presence mode may be {@link Mode#away away},
+     * {@link Mode#xa extended away} or {@link Mode#dnd do not disturb}. Use
+     * {@link #isAway()} to determine if the user is away.
+     *
+     * @return true if the presence type is available.
+     */
+    public boolean isAvailable() {
+        return type == Type.available;    
+    }
+
+    /**
+     * Returns true if the presence type is {@link Type#available available} and the presence
+     * mode is {@link Mode#away away}, {@link Mode#xa extended away}, or
+     * {@link Mode#dnd do not disturb}. False will be returned when the type or mode
+     * is any other value, including when the presence type is unavailable (offline).
+     * This is a convenience method equivalent to
+     * <tt>type == Type.available && (mode == Mode.away || mode == Mode.xa || mode == Mode.dnd)</tt>.
+     *
+     * @return true if the presence type is available and the presence mode is away, xa, or dnd.
+     */
+    public boolean isAway() {
+        return type == Type.available && (mode == Mode.away || mode == Mode.xa || mode == Mode.dnd); 
+    }
+
+    /**
+     * Returns the type of this presence packet.
+     *
+     * @return the type of the presence packet.
+     */
+    public Type getType() {
+        return type;
+    }
+
+    /**
+     * Sets the type of the presence packet.
+     *
+     * @param type the type of the presence packet.
+     */
+    public void setType(Type type) {
+        if(type == null) {
+            throw new NullPointerException("Type cannot be null");
+        }
+        this.type = type;
+    }
+
+    /**
+     * Returns the status message of the presence update, or <tt>null</tt> if there
+     * is not a status. The status is free-form text describing a user's presence
+     * (i.e., "gone to lunch").
+     *
+     * @return the status message.
+     */
+    public String getStatus() {
+        return status;
+    }
+
+    /**
+     * Sets the status message of the presence update. The status is free-form text
+     * describing a user's presence (i.e., "gone to lunch").
+     *
+     * @param status the status message.
+     */
+    public void setStatus(String status) {
+        this.status = status;
+    }
+
+    /**
+     * Returns the priority of the presence, or Integer.MIN_VALUE if no priority has been set.
+     *
+     * @return the priority.
+     */
+    public int getPriority() {
+        return priority;
+    }
+
+    /**
+     * Sets the priority of the presence. The valid range is -128 through 128.
+     *
+     * @param priority the priority of the presence.
+     * @throws IllegalArgumentException if the priority is outside the valid range.
+     */
+    public void setPriority(int priority) {
+        if (priority < -128 || priority > 128) {
+            throw new IllegalArgumentException("Priority value " + priority +
+                    " is not valid. Valid range is -128 through 128.");
+        }
+        this.priority = priority;
+    }
+
+    /**
+     * Returns the mode of the presence update, or <tt>null</tt> if the mode is not set.
+     * A null presence mode value is interpreted to be the same thing as
+     * {@link Presence.Mode#available}.
+     *
+     * @return the mode.
+     */
+    public Mode getMode() {
+        return mode;
+    }
+
+    /**
+     * Sets the mode of the presence update. A null presence mode value is interpreted
+     * to be the same thing as {@link Presence.Mode#available}.
+     *
+     * @param mode the mode.
+     */
+    public void setMode(Mode mode) {
+        this.mode = mode;
+    }
+
+    /**
+     * Returns the xml:lang of this Presence, or null if one has not been set.
+     *
+     * @return the xml:lang of this Presence, or null if one has not been set.
+     * @since 3.0.2
+     */
+    public String getLanguage() {
+        return language;
+    }
+
+    /**
+     * Sets the xml:lang of this Presence.
+     *
+     * @param language the xml:lang of this Presence.
+     * @since 3.0.2
+     */
+    public void setLanguage(String language) {
+        this.language = language;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<presence");
+        if(getXmlns() != null) {
+            buf.append(" xmlns=\"").append(getXmlns()).append("\"");
+        }
+        if (language != null) {
+            buf.append(" xml:lang=\"").append(getLanguage()).append("\"");
+        }
+        if (getPacketID() != null) {
+            buf.append(" id=\"").append(getPacketID()).append("\"");
+        }
+        if (getTo() != null) {
+            buf.append(" to=\"").append(StringUtils.escapeForXML(getTo())).append("\"");
+        }
+        if (getFrom() != null) {
+            buf.append(" from=\"").append(StringUtils.escapeForXML(getFrom())).append("\"");
+        }
+        if (type != Type.available) {
+            buf.append(" type=\"").append(type).append("\"");
+        }
+        buf.append(">");
+        if (status != null) {
+            buf.append("<status>").append(StringUtils.escapeForXML(status)).append("</status>");
+        }
+        if (priority != Integer.MIN_VALUE) {
+            buf.append("<priority>").append(priority).append("</priority>");
+        }
+        if (mode != null && mode != Mode.available) {
+            buf.append("<show>").append(mode).append("</show>");
+        }
+
+        buf.append(this.getExtensionsXML());
+
+        // Add the error sub-packet, if there is one.
+        XMPPError error = getError();
+        if (error != null) {
+            buf.append(error.toXML());
+        }
+
+        buf.append("</presence>");
+        
+        return buf.toString();
+    }
+
+    public String toString() {
+        StringBuilder buf = new StringBuilder();
+        buf.append(type);
+        if (mode != null) {
+            buf.append(": ").append(mode);
+        }
+        if (getStatus() != null) {
+            buf.append(" (").append(getStatus()).append(")");
+        }
+        return buf.toString();
+    }
+
+    /**
+     * A enum to represent the presecence type. Not that presence type is often confused
+     * with presence mode. Generally, if a user is signed into a server, they have a presence
+     * type of {@link #available available}, even if the mode is {@link Mode#away away},
+     * {@link Mode#dnd dnd}, etc. The presence type is only {@link #unavailable unavailable} when
+     * the user is signing out of the server.
+     */
+    public enum Type {
+
+       /**
+        * The user is available to receive messages (default).
+        */
+        available,
+
+        /**
+         * The user is unavailable to receive messages.
+         */
+        unavailable,
+
+        /**
+         * Request subscription to recipient's presence.
+         */
+        subscribe,
+
+        /**
+         * Grant subscription to sender's presence.
+         */
+        subscribed,
+
+        /**
+         * Request removal of subscription to sender's presence.
+         */
+        unsubscribe,
+
+        /**
+         * Grant removal of subscription to sender's presence.
+         */
+        unsubscribed,
+
+        /**
+         * The presence packet contains an error message.
+         */
+        error
+    }
+
+    /**
+     * An enum to represent the presence mode.
+     */
+    public enum Mode {
+
+        /**
+         * Free to chat.
+         */
+        chat,
+
+        /**
+         * Available (the default).
+         */
+        available,
+
+        /**
+         * Away.
+         */
+        away,
+
+        /**
+         * Away for an extended period of time.
+         */
+        xa,
+
+        /**
+         * Do not disturb.
+         */
+        dnd
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/packet/Privacy.java b/src/org/jivesoftware/smack/packet/Privacy.java
new file mode 100644
index 0000000..a62d578
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Privacy.java
@@ -0,0 +1,323 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2006-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import java.util.*;
+
+/**
+ * A Privacy IQ Packet, is used by the {@link org.jivesoftware.smack.PrivacyListManager}
+ * and {@link org.jivesoftware.smack.provider.PrivacyProvider} to allow and block
+ * communications from other users. It contains the appropriate structure to suit
+ * user-defined privacy lists. Different configured Privacy packages are used in the
+ * server & manager communication in order to:
+ * <ul>
+ * <li>Retrieving one's privacy lists. 
+ * <li>Adding, removing, and editing one's privacy lists. 
+ * <li>Setting, changing, or declining active lists. 
+ * <li>Setting, changing, or declining the default list (i.e., the list that is active by default). 
+ * </ul>
+ * Privacy Items can handle different kind of blocking communications based on JID, group, 
+ * subscription type or globally {@link PrivacyItem}
+ * 
+ * @author Francisco Vives
+ */
+public class Privacy extends IQ {
+	/** declineActiveList is true when the user declines the use of the active list **/
+	private boolean declineActiveList=false;
+	/** activeName is the name associated with the active list set for the session **/
+	private String activeName;
+	/** declineDefaultList is true when the user declines the use of the default list **/
+	private boolean declineDefaultList=false;
+	/** defaultName is the name of the default list that applies to the user as a whole **/
+	private String defaultName;
+	/** itemLists holds the set of privacy items classified in lists. It is a map where the 
+	 * key is the name of the list and the value a collection with privacy items. **/
+	private Map<String, List<PrivacyItem>> itemLists = new HashMap<String, List<PrivacyItem>>();
+
+    /**
+     * Set or update a privacy list with privacy items.
+     *
+     * @param listName the name of the new privacy list.
+     * @param listItem the {@link PrivacyItem} that rules the list.
+     * @return the privacy List.
+     */
+    public List<PrivacyItem> setPrivacyList(String listName, List<PrivacyItem> listItem) {
+        // Add new list to the itemLists
+        this.getItemLists().put(listName, listItem);
+        return listItem;
+    }
+
+    /**
+     * Set the active list based on the default list.
+     *
+     * @return the active List.
+     */
+    public List<PrivacyItem> setActivePrivacyList() {
+        this.setActiveName(this.getDefaultName());
+        return this.getItemLists().get(this.getActiveName());
+    }
+
+    /**
+     * Deletes an existing privacy list. If the privacy list being deleted was the default list 
+     * then the user will end up with no default list. Therefore, the user will have to set a new 
+     * default list.
+     *
+     * @param listName the name of the list being deleted.
+     */
+    public void deletePrivacyList(String listName) {
+        // Remove the list from the cache
+    	this.getItemLists().remove(listName);
+
+        // Check if deleted list was the default list
+        if (this.getDefaultName() != null && listName.equals(this.getDefaultName())) {
+        	this.setDefaultName(null);
+        }
+    }
+
+    /**
+     * Returns the active privacy list or <tt>null</tt> if none was found.
+     *
+     * @return list with {@link PrivacyItem} or <tt>null</tt> if none was found.
+     */
+    public List<PrivacyItem> getActivePrivacyList() {
+        // Check if we have the default list
+        if (this.getActiveName() == null) {
+        	return null;
+        } else {
+        	return this.getItemLists().get(this.getActiveName());
+        }
+    }
+
+    /**
+     * Returns the default privacy list or <tt>null</tt> if none was found.
+     *
+     * @return list with {@link PrivacyItem} or <tt>null</tt> if none was found.
+     */
+    public List<PrivacyItem> getDefaultPrivacyList() {
+        // Check if we have the default list
+        if (this.getDefaultName() == null) {
+        	return null;
+        } else {
+        	return this.getItemLists().get(this.getDefaultName());
+        }
+    }
+
+    /**
+     * Returns a specific privacy list.
+     *
+     * @param listName the name of the list to get.
+     * @return a List with {@link PrivacyItem}
+     */
+    public List<PrivacyItem> getPrivacyList(String listName) {
+        return this.getItemLists().get(listName);
+    }
+
+    /**
+     * Returns the privacy item in the specified order.
+     *
+     * @param listName the name of the privacy list.
+     * @param order the order of the element.
+     * @return a List with {@link PrivacyItem}
+     */
+    public PrivacyItem getItem(String listName, int order) {
+    	Iterator<PrivacyItem> values = getPrivacyList(listName).iterator();
+    	PrivacyItem itemFound = null;
+    	while (itemFound == null && values.hasNext()) {
+    		PrivacyItem element = values.next();
+			if (element.getOrder() == order) {
+				itemFound = element;
+			}
+		}
+    	return itemFound;
+    }
+
+    /**
+     * Sets a given privacy list as the new user default list.
+     *
+     * @param newDefault the new default privacy list.
+     * @return if the default list was changed.
+     */
+    public boolean changeDefaultList(String newDefault) {
+        if (this.getItemLists().containsKey(newDefault)) {
+           this.setDefaultName(newDefault);
+           return true;
+        } else {
+        	return false; 
+        }
+    }
+
+    /**
+     * Remove the list.
+     *
+     * @param listName name of the list to remove.
+     */
+     public void deleteList(String listName) {
+    	 this.getItemLists().remove(listName);
+     }
+
+    /**
+     * Returns the name associated with the active list set for the session. Communications
+     * will be verified against the active list.
+     *
+     * @return the name of the active list.
+     */
+	public String getActiveName() {
+		return activeName;
+	}
+
+    /**
+     * Sets the name associated with the active list set for the session. Communications
+     * will be verified against the active list.
+     * 
+     * @param activeName is the name of the active list.
+     */
+	public void setActiveName(String activeName) {
+		this.activeName = activeName;
+	}
+
+    /**
+     * Returns the name of the default list that applies to the user as a whole. Default list is 
+     * processed if there is no active list set for the target session/resource to which a stanza 
+     * is addressed, or if there are no current sessions for the user.
+     * 
+     * @return the name of the default list.
+     */
+	public String getDefaultName() {
+		return defaultName;
+	}
+
+    /**
+     * Sets the name of the default list that applies to the user as a whole. Default list is 
+     * processed if there is no active list set for the target session/resource to which a stanza 
+     * is addressed, or if there are no current sessions for the user.
+     * 
+     * If there is no default list set, then all Privacy Items are processed.
+     * 
+     * @param defaultName is the name of the default list.
+     */
+	public void setDefaultName(String defaultName) {
+		this.defaultName = defaultName;
+	}
+
+    /**
+     * Returns the collection of privacy list that the user holds. A Privacy List contains a set of 
+     * rules that define if communication with the list owner is allowed or denied. 
+     * Users may have zero, one or more privacy items.
+     * 
+     * @return a map where the key is the name of the list and the value the 
+     * collection of privacy items.
+     */
+	public Map<String, List<PrivacyItem>> getItemLists() {
+		return itemLists;
+	}
+
+    /** 
+     * Returns whether the receiver allows or declines the use of an active list.
+     * 
+     * @return the decline status of the list.
+     */
+	public boolean isDeclineActiveList() {
+		return declineActiveList;
+	}
+
+    /** 
+     * Sets whether the receiver allows or declines the use of an active list.
+     * 
+     * @param declineActiveList indicates if the receiver declines the use of an active list.
+     */
+	public void setDeclineActiveList(boolean declineActiveList) {
+		this.declineActiveList = declineActiveList;
+	}
+
+    /** 
+     * Returns whether the receiver allows or declines the use of a default list.
+     * 
+     * @return the decline status of the list.
+     */
+	public boolean isDeclineDefaultList() {
+		return declineDefaultList;
+	}
+
+    /** 
+     * Sets whether the receiver allows or declines the use of a default list.
+     * 
+     * @param declineDefaultList indicates if the receiver declines the use of a default list.
+     */
+	public void setDeclineDefaultList(boolean declineDefaultList) {
+		this.declineDefaultList = declineDefaultList;
+	}
+
+	/** 
+     * Returns all the list names the user has defined to group restrictions.
+     * 
+     * @return a Set with Strings containing every list names.
+     */
+	public Set<String> getPrivacyListNames() {
+		return this.itemLists.keySet();
+	}
+	
+	public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:privacy\">");
+        
+        // Add the active tag
+        if (this.isDeclineActiveList()) {
+        	buf.append("<active/>");
+        } else {
+        	if (this.getActiveName() != null) {
+            	buf.append("<active name=\"").append(this.getActiveName()).append("\"/>");
+            }
+        }
+        // Add the default tag
+        if (this.isDeclineDefaultList()) {
+        	buf.append("<default/>");
+        } else {
+	        if (this.getDefaultName() != null) {
+	        	buf.append("<default name=\"").append(this.getDefaultName()).append("\"/>");
+	        }
+        }
+        
+        // Add the list with their privacy items
+        for (Map.Entry<String, List<PrivacyItem>> entry : this.getItemLists().entrySet()) {
+          String listName = entry.getKey();
+          List<PrivacyItem> items = entry.getValue();
+			// Begin the list tag
+			if (items.isEmpty()) {
+				buf.append("<list name=\"").append(listName).append("\"/>");
+			} else {
+				buf.append("<list name=\"").append(listName).append("\">");
+			}
+	        for (PrivacyItem item : items) {
+	        	// Append the item xml representation
+	        	buf.append(item.toXML());
+	        }
+	        // Close the list tag
+	        if (!items.isEmpty()) {
+				buf.append("</list>");
+			}
+		}
+
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+    
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/packet/PrivacyItem.java b/src/org/jivesoftware/smack/packet/PrivacyItem.java
new file mode 100644
index 0000000..2e144ee
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/PrivacyItem.java
@@ -0,0 +1,462 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.packet;
+
+/**
+ * A privacy item acts a rule that when matched defines if a packet should be blocked or not.
+ *
+ * Privacy Items can handle different kind of blocking communications based on JID, group,
+ * subscription type or globally by:<ul>
+ * <li>Allowing or blocking messages.
+ * <li>Allowing or blocking inbound presence notifications.
+ * <li>Allowing or blocking outbound presence notifications.
+ * <li>Allowing or blocking IQ stanzas.
+ * <li>Allowing or blocking all communications.
+ * </ul>
+ * @author Francisco Vives
+ */
+public class PrivacyItem {
+	/** allow is the action associated with the item, it can allow or deny the communication. */
+	private boolean allow;
+	/** order is a non-negative integer that is unique among all items in the list. */
+    private int order;
+    /** rule hold the kind of communication ([jid|group|subscription]) it will allow or block and
+     * identifier to apply the action.
+     * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+     * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+     * in the user's roster.
+     * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+     * "from", or "none". */
+    private PrivacyRule rule;
+
+    /** blocks incoming IQ stanzas. */
+    private boolean filterIQ = false;
+    /** filterMessage blocks incoming message stanzas. */
+    private boolean filterMessage = false;
+    /** blocks incoming presence notifications. */
+    private boolean filterPresence_in = false;
+    /** blocks outgoing presence notifications. */
+    private boolean filterPresence_out = false;
+
+    /**
+     * Creates a new privacy item.
+     *
+     * @param type the type.
+     */
+    public PrivacyItem(String type, boolean allow, int order) {
+        this.setRule(PrivacyRule.fromString(type));
+        this.setAllow(allow);
+        this.setOrder(order);
+    }
+
+    /**
+     * Returns the action associated with the item, it MUST be filled and will allow or deny
+     * the communication.
+     *
+     * @return the allow communication status.
+     */
+    public boolean isAllow() {
+		return allow;
+	}
+
+    /**
+     * Sets the action associated with the item, it can allow or deny the communication.
+     *
+     * @param allow indicates if the receiver allow or deny the communication.
+     */
+    private void setAllow(boolean allow) {
+		this.allow = allow;
+	}
+
+
+    /**
+     * Returns whether the receiver allow or deny incoming IQ stanzas or not.
+     *
+     * @return the iq filtering status.
+     */
+    public boolean isFilterIQ() {
+		return filterIQ;
+	}
+
+
+    /**
+     * Sets whether the receiver allows or denies incoming IQ stanzas or not.
+     *
+     * @param filterIQ indicates if the receiver allows or denies incoming IQ stanzas.
+     */
+    public void setFilterIQ(boolean filterIQ) {
+		this.filterIQ = filterIQ;
+	}
+
+
+    /**
+     * Returns whether the receiver allows or denies incoming messages or not.
+     *
+     * @return the message filtering status.
+     */
+    public boolean isFilterMessage() {
+		return filterMessage;
+	}
+
+
+    /**
+     * Sets wheather the receiver allows or denies incoming messages or not.
+     *
+     * @param filterMessage indicates if the receiver allows or denies incoming messages or not.
+     */
+    public void setFilterMessage(boolean filterMessage) {
+		this.filterMessage = filterMessage;
+	}
+
+
+    /**
+     * Returns whether the receiver allows or denies incoming presence or not.
+     *
+     * @return the iq filtering incoming presence status.
+     */
+    public boolean isFilterPresence_in() {
+		return filterPresence_in;
+	}
+
+
+    /**
+     * Sets whether the receiver allows or denies incoming presence or not.
+     *
+     * @param filterPresence_in indicates if the receiver allows or denies filtering incoming presence.
+     */
+    public void setFilterPresence_in(boolean filterPresence_in) {
+		this.filterPresence_in = filterPresence_in;
+	}
+
+
+    /**
+     * Returns whether the receiver allows or denies incoming presence or not.
+     *
+     * @return the iq filtering incoming presence status.
+     */
+    public boolean isFilterPresence_out() {
+		return filterPresence_out;
+	}
+
+
+    /**
+     * Sets whether the receiver allows or denies outgoing presence or not.
+     *
+     * @param filterPresence_out indicates if the receiver allows or denies filtering outgoing presence
+     */
+    public void setFilterPresence_out(boolean filterPresence_out) {
+		this.filterPresence_out = filterPresence_out;
+	}
+
+
+    /**
+     * Returns the order where the receiver is processed. List items are processed in
+     * ascending order.
+     *
+     * The order MUST be filled and its value MUST be a non-negative integer
+     * that is unique among all items in the list.
+     *
+     * @return the order number.
+     */
+    public int getOrder() {
+		return order;
+	}
+
+
+    /**
+     * Sets the order where the receiver is processed.
+     *
+     * The order MUST be filled and its value MUST be a non-negative integer
+     * that is unique among all items in the list.
+     *
+     * @param order indicates the order in the list.
+     */
+    public void setOrder(int order) {
+		this.order = order;
+	}
+
+    /**
+     * Sets the element identifier to apply the action.
+     *
+     * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+     * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+     * in the user's roster.
+     * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+     * "from", or "none".
+     *
+     * @param value is the identifier to apply the action.
+     */
+    public void setValue(String value) {
+    	if (!(this.getRule() == null && value == null)) {
+    		this.getRule().setValue(value);
+    	}
+	}
+
+    /**
+     * Returns the type hold the kind of communication it will allow or block.
+     * It MUST be filled with one of these values: jid, group or subscription.
+     *
+     * @return the type of communication it represent.
+     */
+    public Type getType() {
+    	if (this.getRule() == null) {
+    		return null;
+    	} else {
+		return this.getRule().getType();
+    	}
+	}
+
+    /**
+     * Returns the element identifier to apply the action.
+     *
+     * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+     * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+     * in the user's roster.
+     * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+     * "from", or "none".
+     *
+     * @return the identifier to apply the action.
+     */
+    public String getValue() {
+    	if (this.getRule() == null) {
+    		return null;
+    	} else {
+		return this.getRule().getValue();
+    	}
+	}
+
+
+    /**
+     * Returns whether the receiver allows or denies every kind of communication.
+     *
+     * When filterIQ, filterMessage, filterPresence_in and filterPresence_out are not set
+     * the receiver will block all communications.
+     *
+     * @return the all communications status.
+     */
+    public boolean isFilterEverything() {
+		return !(this.isFilterIQ() || this.isFilterMessage() || this.isFilterPresence_in()
+				|| this.isFilterPresence_out());
+	}
+
+
+	private PrivacyRule getRule() {
+		return rule;
+	}
+
+	private void setRule(PrivacyRule rule) {
+		this.rule = rule;
+	}
+	/**
+	 * Answer an xml representation of the receiver according to the RFC 3921.
+	 *
+	 * @return the text xml representation.
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<item");
+        if (this.isAllow()) {
+        	buf.append(" action=\"allow\"");
+        } else {
+        	buf.append(" action=\"deny\"");
+        }
+        buf.append(" order=\"").append(getOrder()).append("\"");
+        if (getType() != null) {
+            buf.append(" type=\"").append(getType()).append("\"");
+        }
+        if (getValue() != null) {
+            buf.append(" value=\"").append(getValue()).append("\"");
+        }
+        if (isFilterEverything()) {
+        	buf.append("/>");
+        } else {
+        	buf.append(">");
+        	if (this.isFilterIQ()) {
+            	buf.append("<iq/>");
+            }
+        	if (this.isFilterMessage()) {
+            	buf.append("<message/>");
+            }
+        	if (this.isFilterPresence_in()) {
+            	buf.append("<presence-in/>");
+            }
+        	if (this.isFilterPresence_out()) {
+            	buf.append("<presence-out/>");
+            }
+        	buf.append("</item>");
+        }
+        return buf.toString();
+    }
+
+
+    /**
+     * Privacy Rule represents the kind of action to apply.
+     * It holds the kind of communication ([jid|group|subscription]) it will allow or block and
+     * identifier to apply the action.
+     */
+
+	public static class PrivacyRule {
+    	 /**
+    	  * Type defines if the rule is based on JIDs, roster groups or presence subscription types.
+    	  * Available values are: [jid|group|subscription]
+    	  */
+         private Type type;
+         /**
+          * The value hold the element identifier to apply the action.
+          * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+          * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+          * in the user's roster.
+          * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+          * "from", or "none".
+          */
+         private String value;
+
+         /**
+     	 * If the type is "subscription", then the 'value' attribute MUST be one of "both",
+     	 * "to", "from", or "none"
+     	 */
+     	public static final String SUBSCRIPTION_BOTH = "both";
+     	public static final String SUBSCRIPTION_TO = "to";
+     	public static final String SUBSCRIPTION_FROM = "from";
+     	public static final String SUBSCRIPTION_NONE = "none";
+
+         /**
+          * Returns the type constant associated with the String value.
+          */
+         protected static PrivacyRule fromString(String value) {
+             if (value == null) {
+                 return null;
+             }
+             PrivacyRule rule = new PrivacyRule();
+             rule.setType(Type.valueOf(value.toLowerCase()));
+             return rule;
+         }
+
+         /**
+          * Returns the type hold the kind of communication it will allow or block.
+          * It MUST be filled with one of these values: jid, group or subscription.
+          *
+          * @return the type of communication it represent.
+          */
+         public Type getType() {
+     		return type;
+     	}
+
+         /**
+          * Sets the action associated with the item, it can allow or deny the communication.
+          *
+          * @param type indicates if the receiver allows or denies the communication.
+          */
+         private void setType(Type type) {
+     		this.type = type;
+     	}
+
+         /**
+          * Returns the element identifier to apply the action.
+          *
+          * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+          * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+          * in the user's roster.
+          * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+          * "from", or "none".
+          *
+          * @return the identifier to apply the action.
+          */
+         public String getValue() {
+     		return value;
+     	}
+
+         /**
+          * Sets the element identifier to apply the action.
+          *
+          * If the type is "jid", then the 'value' attribute MUST contain a valid Jabber ID.
+          * If the type is "group", then the 'value' attribute SHOULD contain the name of a group
+          * in the user's roster.
+          * If the type is "subscription", then the 'value' attribute MUST be one of "both", "to",
+          * "from", or "none".
+          *
+          * @param value is the identifier to apply the action.
+          */
+         protected void setValue(String value) {
+        	 if (this.isSuscription()) {
+        		 setSuscriptionValue(value);
+        	 } else {
+        		 this.value = value;
+        	 }
+     	}
+
+         /**
+          * Sets the element identifier to apply the action.
+          *
+          * The 'value' attribute MUST be one of "both", "to", "from", or "none".
+          *
+          * @param value is the identifier to apply the action.
+          */
+         private void setSuscriptionValue(String value) {
+        	 String setValue;
+             if (value == null) {
+            	 // Do nothing
+             }
+             if (SUBSCRIPTION_BOTH.equalsIgnoreCase(value)) {
+            	 setValue = SUBSCRIPTION_BOTH;
+             }
+             else if (SUBSCRIPTION_TO.equalsIgnoreCase(value)) {
+            	 setValue = SUBSCRIPTION_TO;
+             }
+             else if (SUBSCRIPTION_FROM.equalsIgnoreCase(value)) {
+            	 setValue = SUBSCRIPTION_FROM;
+             }
+             else if (SUBSCRIPTION_NONE.equalsIgnoreCase(value)) {
+            	 setValue = SUBSCRIPTION_NONE;
+             }
+             // Default to available.
+             else {
+            	 setValue = null;
+             }
+     		this.value = setValue;
+     	}
+
+         /**
+          * Returns if the receiver represents a subscription rule.
+          *
+          * @return if the receiver represents a subscription rule.
+          */
+         public boolean isSuscription () {
+     		return this.getType() == Type.subscription;
+     	}
+    }
+
+    /**
+     * Type defines if the rule is based on JIDs, roster groups or presence subscription types.
+     */
+    public static enum Type {
+        /**
+         * JID being analyzed should belong to a roster group of the list's owner.
+         */
+        group,
+        /**
+         * JID being analyzed should have a resource match, domain match or bare JID match.
+         */
+        jid,
+        /**
+         * JID being analyzed should belong to a contact present in the owner's roster with
+         * the specified subscription status.
+         */
+        subscription
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/Registration.java b/src/org/jivesoftware/smack/packet/Registration.java
new file mode 100644
index 0000000..df22e27
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Registration.java
@@ -0,0 +1,155 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Represents registration packets. An empty GET query will cause the server to return information
+ * about it's registration support. SET queries can be used to create accounts or update
+ * existing account information. XMPP servers may require a number of attributes to be set
+ * when creating a new account. The standard account attributes are as follows:
+ * <ul>
+ *      <li>name -- the user's name.
+ *      <li>first -- the user's first name.
+ *      <li>last -- the user's last name.
+ *      <li>email -- the user's email address.
+ *      <li>city -- the user's city.
+ *      <li>state -- the user's state.
+ *      <li>zip -- the user's ZIP code.
+ *      <li>phone -- the user's phone number.
+ *      <li>url -- the user's website.
+ *      <li>date -- the date the registration took place.
+ *      <li>misc -- other miscellaneous information to associate with the account.
+ *      <li>text -- textual information to associate with the account.
+ *      <li>remove -- empty flag to remove account.
+ * </ul>
+ *
+ * @author Matt Tucker
+ */
+public class Registration extends IQ {
+
+    private String instructions = null;
+    private Map<String, String> attributes = new HashMap<String,String>();
+    private List<String> requiredFields = new ArrayList<String>();
+    private boolean registered = false;
+    private boolean remove = false;
+
+    /**
+     * Returns the registration instructions, or <tt>null</tt> if no instructions
+     * have been set. If present, instructions should be displayed to the end-user
+     * that will complete the registration process.
+     *
+     * @return the registration instructions, or <tt>null</tt> if there are none.
+     */
+    public String getInstructions() {
+        return instructions;
+    }
+
+    /**
+     * Sets the registration instructions.
+     *
+     * @param instructions the registration instructions.
+     */
+    public void setInstructions(String instructions) {
+        this.instructions = instructions;
+    }
+
+    /**
+     * Returns the map of String key/value pairs of account attributes.
+     *
+     * @return the account attributes.
+     */
+    public Map<String, String> getAttributes() {
+        return attributes;
+    }
+
+    /**
+     * Sets the account attributes. The map must only contain String key/value pairs.
+     *
+     * @param attributes the account attributes.
+     */
+    public void setAttributes(Map<String, String> attributes) {
+        this.attributes = attributes;
+    }
+    
+    public List<String> getRequiredFields(){
+    	return requiredFields;
+    }
+    
+    public void addAttribute(String key, String value){
+    	attributes.put(key, value);
+    }
+    
+    public void setRegistered(boolean registered){
+    	this.registered = registered;
+    }
+    
+    public boolean isRegistered(){
+    	return this.registered;
+    }
+    
+    public String getField(String key){
+    	return attributes.get(key);
+    }
+    
+    public List<String> getFieldNames(){
+    	return new ArrayList<String>(attributes.keySet());
+    }
+    
+    public void setUsername(String username){
+    	attributes.put("username", username);
+    }
+    
+    public void setPassword(String password){
+    	attributes.put("password", password);
+    }
+    
+    public void setRemove(boolean remove){
+    	this.remove = remove;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:register\">");
+        if (instructions != null && !remove) {
+            buf.append("<instructions>").append(instructions).append("</instructions>");
+        }
+        if (attributes != null && attributes.size() > 0 && !remove) {
+            for (String name : attributes.keySet()) {
+                String value = attributes.get(name);
+                buf.append("<").append(name).append(">");
+                buf.append(value);
+                buf.append("</").append(name).append(">");
+            }
+        }
+        else if(remove){
+        	buf.append("</remove>");
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/packet/RosterPacket.java b/src/org/jivesoftware/smack/packet/RosterPacket.java
new file mode 100644
index 0000000..98483c8
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/RosterPacket.java
@@ -0,0 +1,311 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.*;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+/**
+ * Represents XMPP roster packets.
+ *
+ * @author Matt Tucker
+ */
+public class RosterPacket extends IQ {
+
+    private final List<Item> rosterItems = new ArrayList<Item>();
+    /*
+     * The ver attribute following XEP-0237
+     */
+    private String version;
+
+    /**
+     * Adds a roster item to the packet.
+     *
+     * @param item a roster item.
+     */
+    public void addRosterItem(Item item) {
+        synchronized (rosterItems) {
+            rosterItems.add(item);
+        }
+    }
+    
+    public String getVersion(){
+    	return version;
+    }
+    
+    public void setVersion(String version){
+    	this.version = version;
+    }
+
+    /**
+     * Returns the number of roster items in this roster packet.
+     *
+     * @return the number of roster items.
+     */
+    public int getRosterItemCount() {
+        synchronized (rosterItems) {
+            return rosterItems.size();
+        }
+    }
+
+    /**
+     * Returns an unmodifiable collection for the roster items in the packet.
+     *
+     * @return an unmodifiable collection for the roster items in the packet.
+     */
+    public Collection<Item> getRosterItems() {
+        synchronized (rosterItems) {
+            return Collections.unmodifiableList(new ArrayList<Item>(rosterItems));
+        }
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:roster\" ");
+        if(version!=null){
+        	buf.append(" ver=\""+version+"\" ");
+        }
+        buf.append(">");
+        synchronized (rosterItems) {
+            for (Item entry : rosterItems) {
+                buf.append(entry.toXML());
+            }
+        }
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * A roster item, which consists of a JID, their name, the type of subscription, and
+     * the groups the roster item belongs to.
+     */
+    public static class Item {
+
+        private String user;
+        private String name;
+        private ItemType itemType;
+        private ItemStatus itemStatus;
+        private final Set<String> groupNames;
+
+        /**
+         * Creates a new roster item.
+         *
+         * @param user the user.
+         * @param name the user's name.
+         */
+        public Item(String user, String name) {
+            this.user = user.toLowerCase();
+            this.name = name;
+            itemType = null;
+            itemStatus = null;
+            groupNames = new CopyOnWriteArraySet<String>();
+        }
+
+        /**
+         * Returns the user.
+         *
+         * @return the user.
+         */
+        public String getUser() {
+            return user;
+        }
+
+        /**
+         * Returns the user's name.
+         *
+         * @return the user's name.
+         */
+        public String getName() {
+            return name;
+        }
+
+        /**
+         * Sets the user's name.
+         *
+         * @param name the user's name.
+         */
+        public void setName(String name) {
+            this.name = name;
+        }
+
+        /**
+         * Returns the roster item type.
+         *
+         * @return the roster item type.
+         */
+        public ItemType getItemType() {
+            return itemType;
+        }
+
+        /**
+         * Sets the roster item type.
+         *
+         * @param itemType the roster item type.
+         */
+        public void setItemType(ItemType itemType) {
+            this.itemType = itemType;
+        }
+
+        /**
+         * Returns the roster item status.
+         *
+         * @return the roster item status.
+         */
+        public ItemStatus getItemStatus() {
+            return itemStatus;
+        }
+
+        /**
+         * Sets the roster item status.
+         *
+         * @param itemStatus the roster item status.
+         */
+        public void setItemStatus(ItemStatus itemStatus) {
+            this.itemStatus = itemStatus;
+        }
+
+        /**
+         * Returns an unmodifiable set of the group names that the roster item
+         * belongs to.
+         *
+         * @return an unmodifiable set of the group names.
+         */
+        public Set<String> getGroupNames() {
+            return Collections.unmodifiableSet(groupNames);
+        }
+
+        /**
+         * Adds a group name.
+         *
+         * @param groupName the group name.
+         */
+        public void addGroupName(String groupName) {
+            groupNames.add(groupName);
+        }
+
+        /**
+         * Removes a group name.
+         *
+         * @param groupName the group name.
+         */
+        public void removeGroupName(String groupName) {
+            groupNames.remove(groupName);
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item jid=\"").append(user).append("\"");
+            if (name != null) {
+                buf.append(" name=\"").append(StringUtils.escapeForXML(name)).append("\"");
+            }
+            if (itemType != null) {
+                buf.append(" subscription=\"").append(itemType).append("\"");
+            }
+            if (itemStatus != null) {
+                buf.append(" ask=\"").append(itemStatus).append("\"");
+            }
+            buf.append(">");
+            for (String groupName : groupNames) {
+                buf.append("<group>").append(StringUtils.escapeForXML(groupName)).append("</group>");
+            }
+            buf.append("</item>");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * The subscription status of a roster item. An optional element that indicates
+     * the subscription status if a change request is pending.
+     */
+    public static class ItemStatus {
+
+        /**
+         * Request to subcribe.
+         */
+        public static final ItemStatus SUBSCRIPTION_PENDING = new ItemStatus("subscribe");
+
+        /**
+         * Request to unsubscribe.
+         */
+        public static final ItemStatus UNSUBSCRIPTION_PENDING = new ItemStatus("unsubscribe");
+
+        public static ItemStatus fromString(String value) {
+            if (value == null) {
+                return null;
+            }
+            value = value.toLowerCase();
+            if ("unsubscribe".equals(value)) {
+                return UNSUBSCRIPTION_PENDING;
+            }
+            else if ("subscribe".equals(value)) {
+                return SUBSCRIPTION_PENDING;
+            }
+            else {
+                return null;
+            }
+        }
+
+        private String value;
+
+        /**
+         * Returns the item status associated with the specified string.
+         *
+         * @param value the item status.
+         */
+        private ItemStatus(String value) {
+            this.value = value;
+        }
+
+        public String toString() {
+            return value;
+        }
+    }
+
+    public static enum ItemType {
+
+        /**
+         * The user and subscriber have no interest in each other's presence.
+         */
+        none,
+
+        /**
+         * The user is interested in receiving presence updates from the subscriber.
+         */
+        to,
+
+        /**
+         * The subscriber is interested in receiving presence updates from the user.
+         */
+        from,
+
+        /**
+         * The user and subscriber have a mutual interest in each other's presence.
+         */
+        both,
+
+        /**
+         * The user wishes to stop receiving presence updates from the subscriber.
+         */
+        remove
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/Session.java b/src/org/jivesoftware/smack/packet/Session.java
new file mode 100644
index 0000000..fd403ae
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/Session.java
@@ -0,0 +1,45 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+/**
+ * IQ packet that will be sent to the server to establish a session.<p>
+ *
+ * If a server supports sessions, it MUST include a <i>session</i> element in the
+ * stream features it advertises to a client after the completion of stream authentication.
+ * Upon being informed that session establishment is required by the server the client MUST
+ * establish a session if it desires to engage in instant messaging and presence functionality.<p>
+ *
+ * For more information refer to the following
+ * <a href=http://www.xmpp.org/specs/rfc3921.html#session>link</a>.
+ *
+ * @author Gaston Dombiak
+ */
+public class Session extends IQ {
+
+    public Session() {
+        setType(IQ.Type.SET);
+    }
+
+    public String getChildElementXML() {
+        return "<session xmlns=\"urn:ietf:params:xml:ns:xmpp-session\"/>";
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/StreamError.java b/src/org/jivesoftware/smack/packet/StreamError.java
new file mode 100644
index 0000000..8bb4c75
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/StreamError.java
@@ -0,0 +1,106 @@
+/**
+ * $Revision: 2408 $
+ * $Date: 2004-11-02 20:53:30 -0300 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+/**
+ * Represents a stream error packet. Stream errors are unrecoverable errors where the server
+ * will close the unrelying TCP connection after the stream error was sent to the client.
+ * These is the list of stream errors as defined in the XMPP spec:<p>
+ *
+ * <table border=1>
+ *      <tr><td><b>Code</b></td><td><b>Description</b></td></tr>
+ *      <tr><td> bad-format </td><td> the entity has sent XML that cannot be processed </td></tr>
+ *      <tr><td> unsupported-encoding </td><td>  the entity has sent a namespace prefix that is
+ *          unsupported </td></tr>
+ *      <tr><td> bad-namespace-prefix </td><td> Remote Server Timeout </td></tr>
+ *      <tr><td> conflict </td><td> the server is closing the active stream for this entity
+ *          because a new stream has been initiated that conflicts with the existing
+ *          stream. </td></tr>
+ *      <tr><td> connection-timeout </td><td> the entity has not generated any traffic over
+ *          the stream for some period of time. </td></tr>
+ *      <tr><td> host-gone </td><td> the value of the 'to' attribute provided by the initiating
+ *          entity in the stream header corresponds to a hostname that is no longer hosted by
+ *          the server. </td></tr>
+ *      <tr><td> host-unknown </td><td> the value of the 'to' attribute provided by the
+ *          initiating entity in the stream header does not correspond to a hostname that is
+ *          hosted by the server. </td></tr>
+ *      <tr><td> improper-addressing </td><td> a stanza sent between two servers lacks a 'to'
+ *          or 'from' attribute </td></tr>
+ *      <tr><td> internal-server-error </td><td> the server has experienced a
+ *          misconfiguration. </td></tr>
+ *      <tr><td> invalid-from </td><td> the JID or hostname provided in a 'from' address does
+ *          not match an authorized JID. </td></tr>
+ *      <tr><td> invalid-id </td><td> the stream ID or dialback ID is invalid or does not match
+ *          an ID previously provided. </td></tr>
+ *      <tr><td> invalid-namespace </td><td> the streams namespace name is invalid. </td></tr>
+ *      <tr><td> invalid-xml </td><td> the entity has sent invalid XML over the stream. </td></tr>
+ *      <tr><td> not-authorized </td><td> the entity has attempted to send data before the
+ *          stream has been authenticated </td></tr>
+ *      <tr><td> policy-violation </td><td> the entity has violated some local service
+ *          policy. </td></tr>
+ *      <tr><td> remote-connection-failed </td><td> Rthe server is unable to properly connect
+ *          to a remote entity. </td></tr>
+ *      <tr><td> resource-constraint </td><td> Rthe server lacks the system resources necessary
+ *          to service the stream. </td></tr>
+ *      <tr><td> restricted-xml </td><td> the entity has attempted to send restricted XML
+ *          features. </td></tr>
+ *      <tr><td> see-other-host </td><td>  the server will not provide service to the initiating
+ *          entity but is redirecting traffic to another host. </td></tr>
+ *      <tr><td> system-shutdown </td><td> the server is being shut down and all active streams
+ *          are being closed. </td></tr>
+ *      <tr><td> undefined-condition </td><td> the error condition is not one of those defined
+ *          by the other conditions in this list. </td></tr>
+ *      <tr><td> unsupported-encoding </td><td> the initiating entity has encoded the stream in
+ *          an encoding that is not supported. </td></tr>
+ *      <tr><td> unsupported-stanza-type </td><td> the initiating entity has sent a first-level
+ *          child of the stream that is not supported. </td></tr>
+ *      <tr><td> unsupported-version </td><td> the value of the 'version' attribute provided by
+ *          the initiating entity in the stream header specifies a version of XMPP that is not
+ *          supported. </td></tr>
+ *      <tr><td> xml-not-well-formed </td><td> the initiating entity has sent XML that is
+ *          not well-formed. </td></tr>
+ * </table>
+ *
+ * @author Gaston Dombiak
+ */
+public class StreamError {
+
+    private String code;
+
+    public StreamError(String code) {
+        super();
+        this.code = code;
+    }
+
+    /**
+     * Returns the error code.
+     *
+     * @return the error code.
+     */
+    public String getCode() {
+        return code;
+    }
+
+    public String toString() {
+        StringBuilder txt = new StringBuilder();
+        txt.append("stream:error (").append(code).append(")");
+        return txt.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/XMPPError.java b/src/org/jivesoftware/smack/packet/XMPPError.java
new file mode 100644
index 0000000..770a09c
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/XMPPError.java
@@ -0,0 +1,453 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.packet;
+
+import java.util.*;
+
+/**
+ * Represents a XMPP error sub-packet. Typically, a server responds to a request that has
+ * problems by sending the packet back and including an error packet. Each error has a code, type, 
+ * error condition as well as as an optional text explanation. Typical errors are:<p>
+ *
+ * <table border=1>
+ *      <hr><td><b>Code</b></td><td><b>XMPP Error</b></td><td><b>Type</b></td></hr>
+ *      <tr><td>500</td><td>interna-server-error</td><td>WAIT</td></tr>
+ *      <tr><td>403</td><td>forbidden</td><td>AUTH</td></tr>
+ *      <tr><td>400</td<td>bad-request</td><td>MODIFY</td>></tr>
+ *      <tr><td>404</td><td>item-not-found</td><td>CANCEL</td></tr>
+ *      <tr><td>409</td><td>conflict</td><td>CANCEL</td></tr>
+ *      <tr><td>501</td><td>feature-not-implemented</td><td>CANCEL</td></tr>
+ *      <tr><td>302</td><td>gone</td><td>MODIFY</td></tr>
+ *      <tr><td>400</td><td>jid-malformed</td><td>MODIFY</td></tr>
+ *      <tr><td>406</td><td>no-acceptable</td><td> MODIFY</td></tr>
+ *      <tr><td>405</td><td>not-allowed</td><td>CANCEL</td></tr>
+ *      <tr><td>401</td><td>not-authorized</td><td>AUTH</td></tr>
+ *      <tr><td>402</td><td>payment-required</td><td>AUTH</td></tr>
+ *      <tr><td>404</td><td>recipient-unavailable</td><td>WAIT</td></tr>
+ *      <tr><td>302</td><td>redirect</td><td>MODIFY</td></tr>
+ *      <tr><td>407</td><td>registration-required</td><td>AUTH</td></tr>
+ *      <tr><td>404</td><td>remote-server-not-found</td><td>CANCEL</td></tr>
+ *      <tr><td>504</td><td>remote-server-timeout</td><td>WAIT</td></tr>
+ *      <tr><td>502</td><td>remote-server-error</td><td>CANCEL</td></tr>
+ *      <tr><td>500</td><td>resource-constraint</td><td>WAIT</td></tr>
+ *      <tr><td>503</td><td>service-unavailable</td><td>CANCEL</td></tr>
+ *      <tr><td>407</td><td>subscription-required</td><td>AUTH</td></tr>
+ *      <tr><td>500</td><td>undefined-condition</td><td>WAIT</td></tr>
+ *      <tr><td>400</td><td>unexpected-condition</td><td>WAIT</td></tr>
+ *      <tr><td>408</td><td>request-timeout</td><td>CANCEL</td></tr>
+ * </table>
+ *
+ * @author Matt Tucker
+ */
+public class XMPPError {
+
+    private int code;
+    private Type type;
+    private String condition;
+    private String message;
+    private List<PacketExtension> applicationExtensions = null;
+
+
+    /**
+     * Creates a new error with the specified condition infering the type and code.
+     * If the Condition is predefined, client code should be like:
+     *     new XMPPError(XMPPError.Condition.remote_server_timeout);
+     * If the Condition is not predefined, invocations should be like 
+     *     new XMPPError(new XMPPError.Condition("my_own_error"));
+     * 
+     * @param condition the error condition.
+     */
+    public XMPPError(Condition condition) {
+        this.init(condition);
+        this.message = null;
+    }
+
+    /**
+     * Creates a new error with the specified condition and message infering the type and code.
+     * If the Condition is predefined, client code should be like:
+     *     new XMPPError(XMPPError.Condition.remote_server_timeout, "Error Explanation");
+     * If the Condition is not predefined, invocations should be like 
+     *     new XMPPError(new XMPPError.Condition("my_own_error"), "Error Explanation");
+     *
+     * @param condition the error condition.
+     * @param messageText a message describing the error.
+     */
+    public XMPPError(Condition condition, String messageText) {
+        this.init(condition);
+        this.message = messageText;
+    }
+
+    /**
+     * Creates a new  error with the specified code and no message.
+     *
+     * @param code the error code.
+     * @deprecated new errors should be created using the constructor XMPPError(condition)
+     */
+    public XMPPError(int code) {
+        this.code = code;
+        this.message = null;
+    }
+
+    /**
+     * Creates a new error with the specified code and message.
+     * deprecated
+     *
+     * @param code the error code.
+     * @param message a message describing the error.
+     * @deprecated new errors should be created using the constructor XMPPError(condition, message)
+     */
+    public XMPPError(int code, String message) {
+        this.code = code;
+        this.message = message;
+    }
+
+    /**
+     * Creates a new error with the specified code, type, condition and message.
+     * This constructor is used when the condition is not recognized automatically by XMPPError
+     * i.e. there is not a defined instance of ErrorCondition or it does not applies the default 
+     * specification.
+     * 
+     * @param code the error code.
+     * @param type the error type.
+     * @param condition the error condition.
+     * @param message a message describing the error.
+     * @param extension list of packet extensions
+     */
+    public XMPPError(int code, Type type, String condition, String message,
+            List<PacketExtension> extension) {
+        this.code = code;
+        this.type = type;
+        this.condition = condition;
+        this.message = message;
+        this.applicationExtensions = extension;
+    }
+
+    /**
+     * Initialize the error infering the type and code for the received condition.
+     * 
+     * @param condition the error condition.
+     */
+    private void init(Condition condition) {
+        // Look for the condition and its default code and type
+        ErrorSpecification defaultErrorSpecification = ErrorSpecification.specFor(condition);
+        this.condition = condition.value;
+        if (defaultErrorSpecification != null) {
+            // If there is a default error specification for the received condition,
+            // it get configured with the infered type and code.
+            this.type = defaultErrorSpecification.getType();
+            this.code = defaultErrorSpecification.getCode();
+        }
+    }
+    /**
+     * Returns the error condition.
+     *
+     * @return the error condition.
+     */
+    public String getCondition() {
+        return condition;
+    }
+
+    /**
+     * Returns the error type.
+     *
+     * @return the error type.
+     */
+    public Type getType() {
+        return type;
+    }
+
+    /**
+     * Returns the error code.
+     *
+     * @return the error code.
+     */
+    public int getCode() {
+        return code;
+    }
+
+    /**
+     * Returns the message describing the error, or null if there is no message.
+     *
+     * @return the message describing the error, or null if there is no message.
+     */
+    public String getMessage() {
+        return message;
+    }
+
+    /**
+     * Returns the error as XML.
+     *
+     * @return the error as XML.
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<error code=\"").append(code).append("\"");
+        if (type != null) {
+            buf.append(" type=\"");
+            buf.append(type.name());
+            buf.append("\"");
+        }
+        buf.append(">");
+        if (condition != null) {
+            buf.append("<").append(condition);
+            buf.append(" xmlns=\"urn:ietf:params:xml:ns:xmpp-stanzas\"/>");
+        }
+        if (message != null) {
+            buf.append("<text xml:lang=\"en\" xmlns=\"urn:ietf:params:xml:ns:xmpp-stanzas\">");
+            buf.append(message);
+            buf.append("</text>");
+        }
+        for (PacketExtension element : this.getExtensions()) {
+            buf.append(element.toXML());
+        }
+        buf.append("</error>");
+        return buf.toString();
+    }
+
+    public String toString() {
+        StringBuilder txt = new StringBuilder();
+        if (condition != null) {
+            txt.append(condition);
+        }
+        txt.append("(").append(code).append(")");
+        if (message != null) {
+            txt.append(" ").append(message);
+        }
+        return txt.toString();
+    }
+
+    /**
+     * Returns an Iterator for the error extensions attached to the xmppError.
+     * An application MAY provide application-specific error information by including a 
+     * properly-namespaced child in the error element.
+     *
+     * @return an Iterator for the error extensions.
+     */
+    public synchronized List<PacketExtension> getExtensions() {
+        if (applicationExtensions == null) {
+            return Collections.emptyList();
+        }
+        return Collections.unmodifiableList(applicationExtensions);
+    }
+
+    /**
+     * Returns the first patcket extension that matches the specified element name and
+     * namespace, or <tt>null</tt> if it doesn't exist. 
+     *
+     * @param elementName the XML element name of the packet extension.
+     * @param namespace the XML element namespace of the packet extension.
+     * @return the extension, or <tt>null</tt> if it doesn't exist.
+     */
+    public synchronized PacketExtension getExtension(String elementName, String namespace) {
+        if (applicationExtensions == null || elementName == null || namespace == null) {
+            return null;
+        }
+        for (PacketExtension ext : applicationExtensions) {
+            if (elementName.equals(ext.getElementName()) && namespace.equals(ext.getNamespace())) {
+                return ext;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Adds a packet extension to the error.
+     *
+     * @param extension a packet extension.
+     */
+    public synchronized void addExtension(PacketExtension extension) {
+        if (applicationExtensions == null) {
+            applicationExtensions = new ArrayList<PacketExtension>();
+        }
+        applicationExtensions.add(extension);
+    }
+
+    /**
+     * Set the packet extension to the error.
+     *
+     * @param extension a packet extension.
+     */
+    public synchronized void setExtension(List<PacketExtension> extension) {
+        applicationExtensions = extension;
+    }
+
+    /**
+     * A class to represent the type of the Error. The types are:
+     *
+     * <ul>
+     *      <li>XMPPError.Type.WAIT - retry after waiting (the error is temporary)
+     *      <li>XMPPError.Type.CANCEL - do not retry (the error is unrecoverable)
+     *      <li>XMPPError.Type.MODIFY - retry after changing the data sent
+     *      <li>XMPPError.Type.AUTH - retry after providing credentials
+     *      <li>XMPPError.Type.CONTINUE - proceed (the condition was only a warning)
+     * </ul>
+     */
+    public static enum Type {
+        WAIT,
+        CANCEL,
+        MODIFY,
+        AUTH,
+        CONTINUE
+    }
+
+    /**
+     * A class to represent predefined error conditions.
+     */
+    public static class Condition {
+
+        public static final Condition interna_server_error = new Condition("internal-server-error");
+        public static final Condition forbidden = new Condition("forbidden");
+        public static final Condition bad_request = new Condition("bad-request");
+        public static final Condition conflict = new Condition("conflict");
+        public static final Condition feature_not_implemented = new Condition("feature-not-implemented");
+        public static final Condition gone = new Condition("gone");
+        public static final Condition item_not_found = new Condition("item-not-found");
+        public static final Condition jid_malformed = new Condition("jid-malformed");
+        public static final Condition no_acceptable = new Condition("not-acceptable");
+        public static final Condition not_allowed = new Condition("not-allowed");
+        public static final Condition not_authorized = new Condition("not-authorized");
+        public static final Condition payment_required = new Condition("payment-required");
+        public static final Condition recipient_unavailable = new Condition("recipient-unavailable");
+        public static final Condition redirect = new Condition("redirect");
+        public static final Condition registration_required = new Condition("registration-required");
+        public static final Condition remote_server_error = new Condition("remote-server-error");
+        public static final Condition remote_server_not_found = new Condition("remote-server-not-found");
+        public static final Condition remote_server_timeout = new Condition("remote-server-timeout");
+        public static final Condition resource_constraint = new Condition("resource-constraint");
+        public static final Condition service_unavailable = new Condition("service-unavailable");
+        public static final Condition subscription_required = new Condition("subscription-required");
+        public static final Condition undefined_condition = new Condition("undefined-condition");
+        public static final Condition unexpected_request = new Condition("unexpected-request");
+        public static final Condition request_timeout = new Condition("request-timeout");
+
+        private String value;
+
+        public Condition(String value) {
+            this.value = value;
+        }
+
+        public String toString() {
+            return value;
+        }
+    }
+
+
+    /**
+     * A class to represent the error specification used to infer common usage.
+     */
+    private static class ErrorSpecification {
+        private int code;
+        private Type type;
+        private Condition condition;
+        private static Map<Condition, ErrorSpecification> instances = errorSpecifications();
+
+        private ErrorSpecification(Condition condition, Type type, int code) {
+            this.code = code;
+            this.type = type;
+            this.condition = condition;
+        }
+
+        private static Map<Condition, ErrorSpecification> errorSpecifications() {
+            Map<Condition, ErrorSpecification> instances = new HashMap<Condition, ErrorSpecification>(22);
+            instances.put(Condition.interna_server_error, new ErrorSpecification(
+                    Condition.interna_server_error, Type.WAIT, 500));
+            instances.put(Condition.forbidden, new ErrorSpecification(Condition.forbidden,
+                    Type.AUTH, 403));
+            instances.put(Condition.bad_request, new XMPPError.ErrorSpecification(
+                    Condition.bad_request, Type.MODIFY, 400));
+            instances.put(Condition.item_not_found, new XMPPError.ErrorSpecification(
+                    Condition.item_not_found, Type.CANCEL, 404));
+            instances.put(Condition.conflict, new XMPPError.ErrorSpecification(
+                    Condition.conflict, Type.CANCEL, 409));
+            instances.put(Condition.feature_not_implemented, new XMPPError.ErrorSpecification(
+                    Condition.feature_not_implemented, Type.CANCEL, 501));
+            instances.put(Condition.gone, new XMPPError.ErrorSpecification(
+                    Condition.gone, Type.MODIFY, 302));
+            instances.put(Condition.jid_malformed, new XMPPError.ErrorSpecification(
+                    Condition.jid_malformed, Type.MODIFY, 400));
+            instances.put(Condition.no_acceptable, new XMPPError.ErrorSpecification(
+                    Condition.no_acceptable, Type.MODIFY, 406));
+            instances.put(Condition.not_allowed, new XMPPError.ErrorSpecification(
+                    Condition.not_allowed, Type.CANCEL, 405));
+            instances.put(Condition.not_authorized, new XMPPError.ErrorSpecification(
+                    Condition.not_authorized, Type.AUTH, 401));
+            instances.put(Condition.payment_required, new XMPPError.ErrorSpecification(
+                    Condition.payment_required, Type.AUTH, 402));
+            instances.put(Condition.recipient_unavailable, new XMPPError.ErrorSpecification(
+                    Condition.recipient_unavailable, Type.WAIT, 404));
+            instances.put(Condition.redirect, new XMPPError.ErrorSpecification(
+                    Condition.redirect, Type.MODIFY, 302));
+            instances.put(Condition.registration_required, new XMPPError.ErrorSpecification(
+                    Condition.registration_required, Type.AUTH, 407));
+            instances.put(Condition.remote_server_not_found, new XMPPError.ErrorSpecification(
+                    Condition.remote_server_not_found, Type.CANCEL, 404));
+            instances.put(Condition.remote_server_timeout, new XMPPError.ErrorSpecification(
+                    Condition.remote_server_timeout, Type.WAIT, 504));
+            instances.put(Condition.remote_server_error, new XMPPError.ErrorSpecification(
+                    Condition.remote_server_error, Type.CANCEL, 502));
+            instances.put(Condition.resource_constraint, new XMPPError.ErrorSpecification(
+                    Condition.resource_constraint, Type.WAIT, 500));
+            instances.put(Condition.service_unavailable, new XMPPError.ErrorSpecification(
+                    Condition.service_unavailable, Type.CANCEL, 503));
+            instances.put(Condition.subscription_required, new XMPPError.ErrorSpecification(
+                    Condition.subscription_required, Type.AUTH, 407));
+            instances.put(Condition.undefined_condition, new XMPPError.ErrorSpecification(
+                    Condition.undefined_condition, Type.WAIT, 500));
+            instances.put(Condition.unexpected_request, new XMPPError.ErrorSpecification(
+                    Condition.unexpected_request, Type.WAIT, 400));
+            instances.put(Condition.request_timeout, new XMPPError.ErrorSpecification(
+                    Condition.request_timeout, Type.CANCEL, 408));
+
+            return instances;
+        }
+
+        protected static ErrorSpecification specFor(Condition condition) {
+            return instances.get(condition);
+        }
+
+        /**
+         * Returns the error condition.
+         *
+         * @return the error condition.
+         */
+        protected Condition getCondition() {
+            return condition;
+        }
+
+        /**
+         * Returns the error type.
+         *
+         * @return the error type.
+         */
+        protected Type getType() {
+            return type;
+        }
+
+        /**
+         * Returns the error code.
+         *
+         * @return the error code.
+         */
+        protected int getCode() {
+            return code;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/packet/package.html b/src/org/jivesoftware/smack/packet/package.html
new file mode 100644
index 0000000..18a6405
--- /dev/null
+++ b/src/org/jivesoftware/smack/packet/package.html
@@ -0,0 +1 @@
+<body>XML packets that are part of the XMPP protocol.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/provider/EmbeddedExtensionProvider.java b/src/org/jivesoftware/smack/provider/EmbeddedExtensionProvider.java
new file mode 100644
index 0000000..e7b4b93
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/EmbeddedExtensionProvider.java
@@ -0,0 +1,109 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.provider;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.pubsub.provider.ItemProvider;
+import org.jivesoftware.smackx.pubsub.provider.ItemsProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * 
+ * This class simplifies parsing of embedded elements by using the 
+ * <a href="http://en.wikipedia.org/wiki/Template_method_pattern">Template Method Pattern</a>.  
+ * After extracting the current element attributes and content of any child elements, the template method 
+ * ({@link #createReturnExtension(String, String, Map, List)} is called.  Subclasses
+ * then override this method to create the specific return type.
+ * 
+ * <p>To use this class, you simply register your subclasses as extension providers in the 
+ * <b>smack.properties</b> file.  Then they will be automatically picked up and used to parse
+ * any child elements.  
+ * 
+ * <pre>
+ * For example, given the following message
+ * 
+ * &lt;message from='pubsub.shakespeare.lit' to='francisco@denmark.lit' id='foo&gt;
+ *    &lt;event xmlns='http://jabber.org/protocol/pubsub#event&gt;
+ *       &lt;items node='princely_musings'&gt;
+ *          &lt;item id='asdjkwei3i34234n356'&gt;
+ *             &lt;entry xmlns='http://www.w3.org/2005/Atom'&gt;
+ *                &lt;title&gt;Soliloquy&lt;/title&gt;
+ *                &lt;link rel='alternative' type='text/html'/&gt;
+ *                &lt;id>tag:denmark.lit,2003:entry-32397&lt;/id&gt;
+ *             &lt;/entry&gt;
+ *          &lt;/item&gt;
+ *       &lt;/items&gt;
+ *    &lt;/event&gt;
+ * &lt;/message&gt;
+ * 
+ * I would have a classes
+ * {@link ItemsProvider} extends {@link EmbeddedExtensionProvider}
+ * {@link ItemProvider} extends {@link EmbeddedExtensionProvider}
+ * and
+ * AtomProvider extends {@link PacketExtensionProvider}
+ * 
+ * These classes are then registered in the meta-inf/smack.providers file
+ * as follows.
+ * 
+ *   &lt;extensionProvider&gt;
+ *      &lt;elementName&gt;items&lt;/elementName&gt;
+ *      &lt;namespace&gt;http://jabber.org/protocol/pubsub#event&lt;/namespace&gt;
+ *      &lt;className&gt;org.jivesoftware.smackx.provider.ItemsEventProvider&lt;/className&gt;
+ *   &lt;/extensionProvider&gt;
+ *   &lt;extensionProvider&gt;
+ *       &lt;elementName&gt;item&lt;/elementName&gt;
+ *       &lt;namespace&gt;http://jabber.org/protocol/pubsub#event&lt;/namespace&gt;
+ *       &lt;className&gt;org.jivesoftware.smackx.provider.ItemProvider&lt;/className&gt;
+ *   &lt;/extensionProvider&gt;
+ * 
+ * </pre>
+ * 
+ * @author Robin Collier
+ */
+abstract public class EmbeddedExtensionProvider implements PacketExtensionProvider
+{
+
+	final public PacketExtension parseExtension(XmlPullParser parser) throws Exception
+	{
+        String namespace = parser.getNamespace();
+        String name = parser.getName();
+        Map<String, String> attMap = new HashMap<String, String>();
+        
+        for(int i=0; i<parser.getAttributeCount(); i++)
+        {
+        	attMap.put(parser.getAttributeName(i), parser.getAttributeValue(i));
+        }
+        List<PacketExtension> extensions = new ArrayList<PacketExtension>();
+        
+        do
+        {
+            int tag = parser.next();
+
+            if (tag == XmlPullParser.START_TAG) 
+            	extensions.add(PacketParserUtils.parsePacketExtension(parser.getName(), parser.getNamespace(), parser));
+        } while (!name.equals(parser.getName()));
+
+		return createReturnExtension(name, namespace, attMap, extensions);
+	}
+
+	abstract protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content);
+}
diff --git a/src/org/jivesoftware/smack/provider/IQProvider.java b/src/org/jivesoftware/smack/provider/IQProvider.java
new file mode 100644
index 0000000..936c6be
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/IQProvider.java
@@ -0,0 +1,47 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * An interface for parsing custom IQ packets. Each IQProvider must be registered with
+ * the ProviderManager class for it to be used. Every implementation of this
+ * interface <b>must</b> have a public, no-argument constructor.
+ *
+ * @author Matt Tucker
+ */
+public interface IQProvider {
+
+    /**
+     * Parse the IQ sub-document and create an IQ instance. Each IQ must have a
+     * single child element. At the beginning of the method call, the xml parser
+     * will be positioned at the opening tag of the IQ child element. At the end
+     * of the method call, the parser <b>must</b> be positioned on the closing tag
+     * of the child element.
+     *
+     * @param parser an XML parser.
+     * @return a new IQ instance.
+     * @throws Exception if an error occurs parsing the XML.
+     */
+    public IQ parseIQ(XmlPullParser parser) throws Exception;
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/provider/PacketExtensionProvider.java b/src/org/jivesoftware/smack/provider/PacketExtensionProvider.java
new file mode 100644
index 0000000..8fc0af3
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/PacketExtensionProvider.java
@@ -0,0 +1,46 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * An interface for parsing custom packets extensions. Each PacketExtensionProvider must
+ * be registered with the ProviderManager class for it to be used. Every implementation
+ * of this interface <b>must</b> have a public, no-argument constructor.
+ *
+ * @author Matt Tucker
+ */
+public interface PacketExtensionProvider {
+
+    /**
+     * Parse an extension sub-packet and create a PacketExtension instance. At
+     * the beginning of the method call, the xml parser will be positioned on the
+     * opening element of the packet extension. At the end of the method call, the
+     * parser <b>must</b> be positioned on the closing element of the packet extension.
+     *
+     * @param parser an XML parser.
+     * @return a new IQ instance.
+     * @throws java.lang.Exception if an error occurs parsing the XML.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception;
+}
diff --git a/src/org/jivesoftware/smack/provider/PrivacyProvider.java b/src/org/jivesoftware/smack/provider/PrivacyProvider.java
new file mode 100644
index 0000000..62b3120
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/PrivacyProvider.java
@@ -0,0 +1,151 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.provider;
+
+import org.jivesoftware.smack.packet.DefaultPacketExtension;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Privacy;
+import org.jivesoftware.smack.packet.PrivacyItem;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+
+/**
+ * The PrivacyProvider parses {@link Privacy} packets. {@link Privacy}
+ * Parses the <tt>query</tt> sub-document and creates an instance of {@link Privacy}.
+ * For each <tt>item</tt> in the <tt>list</tt> element, it creates an instance 
+ * of {@link PrivacyItem} and {@link org.jivesoftware.smack.packet.PrivacyItem.PrivacyRule}.
+ * 
+ * @author Francisco Vives
+ */
+public class PrivacyProvider implements IQProvider {
+
+	public PrivacyProvider() {
+	}
+
+	public IQ parseIQ(XmlPullParser parser) throws Exception {
+        Privacy privacy = new Privacy();
+        /* privacy.addExtension(PacketParserUtils.parsePacketExtension(parser
+                .getName(), parser.getNamespace(), parser)); */
+        privacy.addExtension(new DefaultPacketExtension(parser.getName(), parser.getNamespace()));
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("active")) {
+                	String activeName = parser.getAttributeValue("", "name");
+                	if (activeName == null) {
+                		privacy.setDeclineActiveList(true);
+                	} else {
+                		privacy.setActiveName(activeName);
+                	}
+                }
+                else if (parser.getName().equals("default")) {
+                	String defaultName = parser.getAttributeValue("", "name");
+                	if (defaultName == null) {
+                		privacy.setDeclineDefaultList(true);
+                	} else {
+                		privacy.setDefaultName(defaultName);
+                	}
+                }
+                else if (parser.getName().equals("list")) {
+                    parseList(parser, privacy);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+
+        return privacy;
+	}
+	
+	// Parse the list complex type
+	public void parseList(XmlPullParser parser, Privacy privacy) throws Exception {
+        boolean done = false;
+        String listName = parser.getAttributeValue("", "name");
+        ArrayList<PrivacyItem> items = new ArrayList<PrivacyItem>();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                	items.add(parseItem(parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("list")) {
+                    done = true;
+                }
+            }
+        }
+
+        privacy.setPrivacyList(listName, items);
+	}
+	
+	// Parse the list complex type
+	public PrivacyItem parseItem(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        // Retrieves the required attributes
+        String actionValue = parser.getAttributeValue("", "action");
+        String orderValue = parser.getAttributeValue("", "order");
+        String type = parser.getAttributeValue("", "type");
+        
+        /* 
+         * According the action value it sets the allow status. The fall-through action is assumed 
+         * to be "allow"
+         */
+        boolean allow = true;
+        if ("allow".equalsIgnoreCase(actionValue)) {
+        	allow = true;
+        } else if ("deny".equalsIgnoreCase(actionValue)) {
+        	allow = false;
+        }
+        // Set the order number
+        int order = Integer.parseInt(orderValue);
+
+        // Create the privacy item
+        PrivacyItem item = new PrivacyItem(type, allow, order);
+        item.setValue(parser.getAttributeValue("", "value"));
+
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("iq")) {
+                	item.setFilterIQ(true);
+                }
+                if (parser.getName().equals("message")) {
+                	item.setFilterMessage(true);
+                }
+                if (parser.getName().equals("presence-in")) {
+                	item.setFilterPresence_in(true);
+                }
+                if (parser.getName().equals("presence-out")) {
+                	item.setFilterPresence_out(true);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    done = true;
+                }
+            }
+        }
+        return item;
+	}
+}
diff --git a/src/org/jivesoftware/smack/provider/ProviderManager.java b/src/org/jivesoftware/smack/provider/ProviderManager.java
new file mode 100644
index 0000000..4ddc8ad
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/ProviderManager.java
@@ -0,0 +1,438 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.io.InputStream;
+import java.net.URL;
+import java.util.*;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * Manages providers for parsing custom XML sub-documents of XMPP packets. Two types of
+ * providers exist:<ul>
+ *      <li>IQProvider -- parses IQ requests into Java objects.
+ *      <li>PacketExtension -- parses XML sub-documents attached to packets into
+ *          PacketExtension instances.</ul>
+ *
+ * <b>IQProvider</b><p>
+ *
+ * By default, Smack only knows how to process IQ packets with sub-packets that
+ * are in a few namespaces such as:<ul>
+ *      <li>jabber:iq:auth
+ *      <li>jabber:iq:roster
+ *      <li>jabber:iq:register</ul>
+ *
+ * Because many more IQ types are part of XMPP and its extensions, a pluggable IQ parsing
+ * mechanism is provided. IQ providers are registered programatically or by creating a
+ * smack.providers file in the META-INF directory of your JAR file. The file is an XML
+ * document that contains one or more iqProvider entries, as in the following example:
+ *
+ * <pre>
+ * &lt;?xml version="1.0"?&gt;
+ * &lt;smackProviders&gt;
+ *     &lt;iqProvider&gt;
+ *         &lt;elementName&gt;query&lt;/elementName&gt;
+ *         &lt;namespace&gt;jabber:iq:time&lt;/namespace&gt;
+ *         &lt;className&gt;org.jivesoftware.smack.packet.Time&lt/className&gt;
+ *     &lt;/iqProvider&gt;
+ * &lt;/smackProviders&gt;</pre>
+ *
+ * Each IQ provider is associated with an element name and a namespace. If multiple provider
+ * entries attempt to register to handle the same namespace, the first entry loaded from the
+ * classpath will take precedence. The IQ provider class can either implement the IQProvider
+ * interface, or extend the IQ class. In the former case, each IQProvider is responsible for
+ * parsing the raw XML stream to create an IQ instance. In the latter case, bean introspection
+ * is used to try to automatically set properties of the IQ instance using the values found
+ * in the IQ packet XML. For example, an XMPP time packet resembles the following:
+ * <pre>
+ * &lt;iq type='result' to='joe@example.com' from='mary@example.com' id='time_1'&gt;
+ *     &lt;query xmlns='jabber:iq:time'&gt;
+ *         &lt;utc&gt;20020910T17:58:35&lt;/utc&gt;
+ *         &lt;tz&gt;MDT&lt;/tz&gt;
+ *         &lt;display&gt;Tue Sep 10 12:58:35 2002&lt;/display&gt;
+ *     &lt;/query&gt;
+ * &lt;/iq&gt;</pre>
+ *
+ * In order for this packet to be automatically mapped to the Time object listed in the
+ * providers file above, it must have the methods setUtc(String), setTz(String), and
+ * setDisplay(String). The introspection service will automatically try to convert the String
+ * value from the XML into a boolean, int, long, float, double, or Class depending on the
+ * type the IQ instance expects.<p>
+ *
+ * A pluggable system for packet extensions, child elements in a custom namespace for
+ * message and presence packets, also exists. Each extension provider
+ * is registered with a name space in the smack.providers file as in the following example:
+ *
+ * <pre>
+ * &lt;?xml version="1.0"?&gt;
+ * &lt;smackProviders&gt;
+ *     &lt;extensionProvider&gt;
+ *         &lt;elementName&gt;x&lt;/elementName&gt;
+ *         &lt;namespace&gt;jabber:iq:event&lt;/namespace&gt;
+ *         &lt;className&gt;org.jivesoftware.smack.packet.MessageEvent&lt/className&gt;
+ *     &lt;/extensionProvider&gt;
+ * &lt;/smackProviders&gt;</pre>
+ *
+ * If multiple provider entries attempt to register to handle the same element name and namespace,
+ * the first entry loaded from the classpath will take precedence. Whenever a packet extension
+ * is found in a packet, parsing will be passed to the correct provider. Each provider
+ * can either implement the PacketExtensionProvider interface or be a standard Java Bean. In
+ * the former case, each extension provider is responsible for parsing the raw XML stream to
+ * contruct an object. In the latter case, bean introspection is used to try to automatically
+ * set the properties of the class using the values in the packet extension sub-element. When an
+ * extension provider is not registered for an element name and namespace combination, Smack will
+ * store all top-level elements of the sub-packet in DefaultPacketExtension object and then
+ * attach it to the packet.<p>
+ *
+ * It is possible to provide a custom provider manager instead of the default implementation
+ * provided by Smack. If you want to provide your own provider manager then you need to do it
+ * before creating any {@link org.jivesoftware.smack.Connection} by sending the static
+ * {@link #setInstance(ProviderManager)} message. Trying to change the provider manager after
+ * an Connection was created will result in an {@link IllegalStateException} error.
+ *
+ * @author Matt Tucker
+ */
+public class ProviderManager {
+
+    private static ProviderManager instance;
+
+    private Map<String, Object> extensionProviders = new ConcurrentHashMap<String, Object>();
+    private Map<String, Object> iqProviders = new ConcurrentHashMap<String, Object>();
+
+    /**
+     * Returns the only ProviderManager valid instance.  Use {@link #setInstance(ProviderManager)}
+     * to configure your own provider manager. If non was provided then an instance of this
+     * class will be used.
+     *
+     * @return the only ProviderManager valid instance.
+     */
+    public static synchronized ProviderManager getInstance() {
+        if (instance == null) {
+            instance = new ProviderManager();
+        }
+        return instance;
+    }
+
+    /**
+     * Sets the only ProviderManager valid instance to be used by all Connections. If you
+     * want to provide your own provider manager then you need to do it before creating
+     * any Connection. Otherwise an IllegalStateException will be thrown.
+     *
+     * @param providerManager the only ProviderManager valid instance to be used.
+     * @throws IllegalStateException if a provider manager was already configued.
+     */
+    public static synchronized void setInstance(ProviderManager providerManager) {
+        if (instance != null) {
+            throw new IllegalStateException("ProviderManager singleton already set");
+        }
+        instance = providerManager;
+    }
+
+    protected void initialize() {
+        // Load IQ processing providers.
+        try {
+            // Get an array of class loaders to try loading the providers files from.
+            ClassLoader[] classLoaders = getClassLoaders();
+            for (ClassLoader classLoader : classLoaders) {
+                Enumeration<URL> providerEnum = classLoader.getResources(
+                        "META-INF/smack.providers");
+                while (providerEnum.hasMoreElements()) {
+                    URL url = providerEnum.nextElement();
+                    InputStream providerStream = null;
+                    try {
+                        providerStream = url.openStream();
+                        XmlPullParser parser = XmlPullParserFactory.newInstance().newPullParser();
+                        parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+                        parser.setInput(providerStream, "UTF-8");
+                        int eventType = parser.getEventType();
+                        do {
+                            if (eventType == XmlPullParser.START_TAG) {
+                                if (parser.getName().equals("iqProvider")) {
+                                    parser.next();
+                                    parser.next();
+                                    String elementName = parser.nextText();
+                                    parser.next();
+                                    parser.next();
+                                    String namespace = parser.nextText();
+                                    parser.next();
+                                    parser.next();
+                                    String className = parser.nextText();
+                                    // Only add the provider for the namespace if one isn't
+                                    // already registered.
+                                    String key = getProviderKey(elementName, namespace);
+                                    if (!iqProviders.containsKey(key)) {
+                                        // Attempt to load the provider class and then create
+                                        // a new instance if it's an IQProvider. Otherwise, if it's
+                                        // an IQ class, add the class object itself, then we'll use
+                                        // reflection later to create instances of the class.
+                                        try {
+                                            // Add the provider to the map.
+                                            Class<?> provider = Class.forName(className);
+                                            if (IQProvider.class.isAssignableFrom(provider)) {
+                                                iqProviders.put(key, provider.newInstance());
+                                            }
+                                            else if (IQ.class.isAssignableFrom(provider)) {
+                                                iqProviders.put(key, provider);
+                                            }
+                                        }
+                                        catch (ClassNotFoundException cnfe) {
+                                            cnfe.printStackTrace();
+                                        }
+                                    }
+                                }
+                                else if (parser.getName().equals("extensionProvider")) {
+                                    parser.next();
+                                    parser.next();
+                                    String elementName = parser.nextText();
+                                    parser.next();
+                                    parser.next();
+                                    String namespace = parser.nextText();
+                                    parser.next();
+                                    parser.next();
+                                    String className = parser.nextText();
+                                    // Only add the provider for the namespace if one isn't
+                                    // already registered.
+                                    String key = getProviderKey(elementName, namespace);
+                                    if (!extensionProviders.containsKey(key)) {
+                                        // Attempt to load the provider class and then create
+                                        // a new instance if it's a Provider. Otherwise, if it's
+                                        // a PacketExtension, add the class object itself and
+                                        // then we'll use reflection later to create instances
+                                        // of the class.
+                                        try {
+                                            // Add the provider to the map.
+                                            Class<?> provider = Class.forName(className);
+                                            if (PacketExtensionProvider.class.isAssignableFrom(
+                                                    provider)) {
+                                                extensionProviders.put(key, provider.newInstance());
+                                            }
+                                            else if (PacketExtension.class.isAssignableFrom(
+                                                    provider)) {
+                                                extensionProviders.put(key, provider);
+                                            }
+                                        }
+                                        catch (ClassNotFoundException cnfe) {
+                                            cnfe.printStackTrace();
+                                        }
+                                    }
+                                }
+                            }
+                            eventType = parser.next();
+                        }
+                        while (eventType != XmlPullParser.END_DOCUMENT);
+                    }
+                    finally {
+                        try {
+                            providerStream.close();
+                        }
+                        catch (Exception e) {
+                            // Ignore.
+                        }
+                    }
+                }
+            }
+        }
+        catch (Exception e) {
+            e.printStackTrace();
+        }
+    }
+
+    /**
+     * Returns the IQ provider registered to the specified XML element name and namespace.
+     * For example, if a provider was registered to the element name "query" and the
+     * namespace "jabber:iq:time", then the following packet would trigger the provider:
+     *
+     * <pre>
+     * &lt;iq type='result' to='joe@example.com' from='mary@example.com' id='time_1'&gt;
+     *     &lt;query xmlns='jabber:iq:time'&gt;
+     *         &lt;utc&gt;20020910T17:58:35&lt;/utc&gt;
+     *         &lt;tz&gt;MDT&lt;/tz&gt;
+     *         &lt;display&gt;Tue Sep 10 12:58:35 2002&lt;/display&gt;
+     *     &lt;/query&gt;
+     * &lt;/iq&gt;</pre>
+     *
+     * <p>Note: this method is generally only called by the internal Smack classes.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     * @return the IQ provider.
+     */
+    public Object getIQProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        return iqProviders.get(key);
+    }
+
+    /**
+     * Returns an unmodifiable collection of all IQProvider instances. Each object
+     * in the collection will either be an IQProvider instance, or a Class object
+     * that implements the IQProvider interface.
+     *
+     * @return all IQProvider instances.
+     */
+    public Collection<Object> getIQProviders() {
+        return Collections.unmodifiableCollection(iqProviders.values());
+    }
+
+    /**
+     * Adds an IQ provider (must be an instance of IQProvider or Class object that is an IQ)
+     * with the specified element name and name space. The provider will override any providers
+     * loaded through the classpath.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     * @param provider the IQ provider.
+     */
+    public void addIQProvider(String elementName, String namespace,
+            Object provider)
+    {
+        if (!(provider instanceof IQProvider || (provider instanceof Class &&
+                IQ.class.isAssignableFrom((Class<?>)provider))))
+        {
+            throw new IllegalArgumentException("Provider must be an IQProvider " +
+                    "or a Class instance.");
+        }
+        String key = getProviderKey(elementName, namespace);
+        iqProviders.put(key, provider);
+    }
+
+    /**
+     * Removes an IQ provider with the specified element name and namespace. This
+     * method is typically called to cleanup providers that are programatically added
+     * using the {@link #addIQProvider(String, String, Object) addIQProvider} method.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     */
+    public void removeIQProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        iqProviders.remove(key);
+    }
+
+    /**
+     * Returns the packet extension provider registered to the specified XML element name
+     * and namespace. For example, if a provider was registered to the element name "x" and the
+     * namespace "jabber:x:event", then the following packet would trigger the provider:
+     *
+     * <pre>
+     * &lt;message to='romeo@montague.net' id='message_1'&gt;
+     *     &lt;body&gt;Art thou not Romeo, and a Montague?&lt;/body&gt;
+     *     &lt;x xmlns='jabber:x:event'&gt;
+     *         &lt;composing/&gt;
+     *     &lt;/x&gt;
+     * &lt;/message&gt;</pre>
+     *
+     * <p>Note: this method is generally only called by the internal Smack classes.
+     *
+     * @param elementName element name associated with extension provider.
+     * @param namespace namespace associated with extension provider.
+     * @return the extenion provider.
+     */
+    public Object getExtensionProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        return extensionProviders.get(key);
+    }
+
+    /**
+     * Adds an extension provider with the specified element name and name space. The provider
+     * will override any providers loaded through the classpath. The provider must be either
+     * a PacketExtensionProvider instance, or a Class object of a Javabean.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     * @param provider the extension provider.
+     */
+    public void addExtensionProvider(String elementName, String namespace,
+            Object provider)
+    {
+        if (!(provider instanceof PacketExtensionProvider || provider instanceof Class)) {
+            throw new IllegalArgumentException("Provider must be a PacketExtensionProvider " +
+                    "or a Class instance.");
+        }
+        String key = getProviderKey(elementName, namespace);
+        extensionProviders.put(key, provider);
+    }
+
+    /**
+     * Removes an extension provider with the specified element name and namespace. This
+     * method is typically called to cleanup providers that are programatically added
+     * using the {@link #addExtensionProvider(String, String, Object) addExtensionProvider} method.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     */
+    public void removeExtensionProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        extensionProviders.remove(key);
+    }
+
+    /**
+     * Returns an unmodifiable collection of all PacketExtensionProvider instances. Each object
+     * in the collection will either be a PacketExtensionProvider instance, or a Class object
+     * that implements the PacketExtensionProvider interface.
+     *
+     * @return all PacketExtensionProvider instances.
+     */
+    public Collection<Object> getExtensionProviders() {
+        return Collections.unmodifiableCollection(extensionProviders.values());
+    }
+
+    /**
+     * Returns a String key for a given element name and namespace.
+     *
+     * @param elementName the element name.
+     * @param namespace the namespace.
+     * @return a unique key for the element name and namespace pair.
+     */
+    private String getProviderKey(String elementName, String namespace) {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(elementName).append("/><").append(namespace).append("/>");
+        return buf.toString();
+    }
+
+    /**
+     * Returns an array of class loaders to load resources from.
+     *
+     * @return an array of ClassLoader instances.
+     */
+    private ClassLoader[] getClassLoaders() {
+        ClassLoader[] classLoaders = new ClassLoader[2];
+        classLoaders[0] = ProviderManager.class.getClassLoader();
+        classLoaders[1] = Thread.currentThread().getContextClassLoader();
+        // Clean up possible null values. Note that #getClassLoader may return a null value.
+        List<ClassLoader> loaders = new ArrayList<ClassLoader>();
+        for (ClassLoader classLoader : classLoaders) {
+            if (classLoader != null) {
+                loaders.add(classLoader);
+            }
+        }
+        return loaders.toArray(new ClassLoader[loaders.size()]);
+    }
+
+    private ProviderManager() {
+        super();
+        initialize();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/provider/package.html b/src/org/jivesoftware/smack/provider/package.html
new file mode 100644
index 0000000..fccc383
--- /dev/null
+++ b/src/org/jivesoftware/smack/provider/package.html
@@ -0,0 +1 @@
+<body>Provides pluggable parsing of incoming IQ's and packet extensions.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/proxy/DirectSocketFactory.java b/src/org/jivesoftware/smack/proxy/DirectSocketFactory.java
new file mode 100644
index 0000000..6197c38
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/DirectSocketFactory.java
@@ -0,0 +1,74 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import java.io.IOException;
+import java.net.InetAddress;
+import java.net.InetSocketAddress;
+import java.net.Proxy;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import javax.net.SocketFactory;
+
+/**
+ * SocketFactory for direct connection
+ * 
+ * @author Atul Aggarwal
+ */
+class DirectSocketFactory 
+    extends SocketFactory
+{
+
+    public DirectSocketFactory()
+    {
+    }
+
+    static private int roundrobin = 0;
+
+    public Socket createSocket(String host, int port) 
+        throws IOException, UnknownHostException
+    {
+        Socket newSocket = new Socket(Proxy.NO_PROXY);
+        InetAddress resolved[] = InetAddress.getAllByName(host);
+        newSocket.connect(new InetSocketAddress(resolved[(roundrobin++) % resolved.length],port));
+        return newSocket;
+    }
+
+    public Socket createSocket(String host ,int port, InetAddress localHost,
+                                int localPort)
+        throws IOException, UnknownHostException
+    {
+        return new Socket(host,port,localHost,localPort);
+    }
+
+    public Socket createSocket(InetAddress host, int port)
+        throws IOException
+    {
+        Socket newSocket = new Socket(Proxy.NO_PROXY);
+        newSocket.connect(new InetSocketAddress(host,port));
+        return newSocket;
+    }
+
+    public Socket createSocket( InetAddress address, int port, 
+                                InetAddress localAddress, int localPort) 
+        throws IOException
+    {
+        return new Socket(address,port,localAddress,localPort);
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/proxy/HTTPProxySocketFactory.java b/src/org/jivesoftware/smack/proxy/HTTPProxySocketFactory.java
new file mode 100644
index 0000000..4ee5dd6
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/HTTPProxySocketFactory.java
@@ -0,0 +1,172 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.StringReader;
+import java.net.HttpURLConnection;
+import java.net.InetAddress;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import javax.net.SocketFactory;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Http Proxy Socket Factory which returns socket connected to Http Proxy
+ * 
+ * @author Atul Aggarwal
+ */
+class HTTPProxySocketFactory 
+    extends SocketFactory
+{
+
+    private ProxyInfo proxy;
+
+    public HTTPProxySocketFactory(ProxyInfo proxy)
+    {
+        this.proxy = proxy;
+    }
+
+    public Socket createSocket(String host, int port) 
+        throws IOException, UnknownHostException
+    {
+        return httpProxifiedSocket(host, port);
+    }
+
+    public Socket createSocket(String host ,int port, InetAddress localHost,
+                                int localPort)
+        throws IOException, UnknownHostException
+    {
+        return httpProxifiedSocket(host, port);
+    }
+
+    public Socket createSocket(InetAddress host, int port)
+        throws IOException
+    {
+        return httpProxifiedSocket(host.getHostAddress(), port);
+        
+    }
+
+    public Socket createSocket( InetAddress address, int port, 
+                                InetAddress localAddress, int localPort) 
+        throws IOException
+    {
+        return httpProxifiedSocket(address.getHostAddress(), port);
+    }
+  
+    private Socket httpProxifiedSocket(String host, int port)
+        throws IOException 
+    {
+        String proxyhost = proxy.getProxyAddress();
+        int proxyPort = proxy.getProxyPort();
+        Socket socket = new Socket(proxyhost,proxyPort);
+        String hostport = "CONNECT " + host + ":" + port;
+        String proxyLine;
+        String username = proxy.getProxyUsername();
+        if (username == null)
+        {
+            proxyLine = "";
+        }
+        else
+        {
+            String password = proxy.getProxyPassword();
+            proxyLine = "\r\nProxy-Authorization: Basic " + StringUtils.encodeBase64(username + ":" + password);
+        }
+        socket.getOutputStream().write((hostport + " HTTP/1.1\r\nHost: "
+            + hostport + proxyLine + "\r\n\r\n").getBytes("UTF-8"));
+        
+        InputStream in = socket.getInputStream();
+        StringBuilder got = new StringBuilder(100);
+        int nlchars = 0;
+        
+        while (true)
+        {
+            char c = (char) in.read();
+            got.append(c);
+            if (got.length() > 1024)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.HTTP, "Recieved " +
+                    "header of >1024 characters from "
+                    + proxyhost + ", cancelling connection");
+            }
+            if (c == -1)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.HTTP);
+            }
+            if ((nlchars == 0 || nlchars == 2) && c == '\r')
+            {
+                nlchars++;
+            }
+            else if ((nlchars == 1 || nlchars == 3) && c == '\n')
+            {
+                nlchars++;
+            }
+            else
+            {
+                nlchars = 0;
+            }
+            if (nlchars == 4)
+            {
+                break;
+            }
+        }
+
+        if (nlchars != 4)
+        {
+            throw new ProxyException(ProxyInfo.ProxyType.HTTP, "Never " +
+                "received blank line from " 
+                + proxyhost + ", cancelling connection");
+        }
+
+        String gotstr = got.toString();
+        
+        BufferedReader br = new BufferedReader(new StringReader(gotstr));
+        String response = br.readLine();
+        
+        if (response == null)
+        {
+            throw new ProxyException(ProxyInfo.ProxyType.HTTP, "Empty proxy " +
+                "response from " + proxyhost + ", cancelling");
+        }
+        
+        Matcher m = RESPONSE_PATTERN.matcher(response);
+        if (!m.matches())
+        {
+            throw new ProxyException(ProxyInfo.ProxyType.HTTP , "Unexpected " +
+                "proxy response from " + proxyhost + ": " + response);
+        }
+        
+        int code = Integer.parseInt(m.group(1));
+        
+        if (code != HttpURLConnection.HTTP_OK)
+        {
+            throw new ProxyException(ProxyInfo.ProxyType.HTTP);
+        }
+        
+        return socket;
+    }
+
+    private static final Pattern RESPONSE_PATTERN
+        = Pattern.compile("HTTP/\\S+\\s(\\d+)\\s(.*)\\s*");
+
+}
diff --git a/src/org/jivesoftware/smack/proxy/ProxyException.java b/src/org/jivesoftware/smack/proxy/ProxyException.java
new file mode 100644
index 0000000..b37910c
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/ProxyException.java
@@ -0,0 +1,44 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import java.io.IOException;
+
+/**
+ * An exception class to handle exceptions caused by proxy.
+ * 
+ * @author Atul Aggarwal
+ */
+public class ProxyException 
+    extends IOException
+{
+    public ProxyException(ProxyInfo.ProxyType type, String ex, Throwable cause)
+    {
+        super("Proxy Exception " + type.toString() + " : "+ex+", "+cause);
+    }
+    
+    public ProxyException(ProxyInfo.ProxyType type, String ex)
+    {
+        super("Proxy Exception " + type.toString() + " : "+ex);
+    }
+    
+    public ProxyException(ProxyInfo.ProxyType type)
+    {
+        super("Proxy Exception " + type.toString() + " : " + "Unknown Error");
+    }
+}
diff --git a/src/org/jivesoftware/smack/proxy/ProxyInfo.java b/src/org/jivesoftware/smack/proxy/ProxyInfo.java
new file mode 100644
index 0000000..5a7d354
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/ProxyInfo.java
@@ -0,0 +1,131 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import javax.net.SocketFactory;
+
+/**
+ * Class which stores proxy information such as proxy type, host, port, 
+ * authentication etc.
+ * 
+ * @author Atul Aggarwal
+ */
+
+public class ProxyInfo
+{
+    public static enum ProxyType
+    {
+        NONE,
+        HTTP,
+        SOCKS4,
+        SOCKS5
+    }
+    
+    private String proxyAddress;
+    private int proxyPort;
+    private String proxyUsername;
+    private String proxyPassword;
+    private ProxyType proxyType;
+    
+    public ProxyInfo(   ProxyType pType, String pHost, int pPort, String pUser, 
+                        String pPass)
+    {
+        this.proxyType = pType;
+        this.proxyAddress = pHost;
+        this.proxyPort = pPort;
+        this.proxyUsername = pUser;
+        this.proxyPassword = pPass;
+    }
+    
+    public static ProxyInfo forHttpProxy(String pHost, int pPort, String pUser, 
+                                    String pPass)
+    {
+        return new ProxyInfo(ProxyType.HTTP, pHost, pPort, pUser, pPass);
+    }
+    
+    public static ProxyInfo forSocks4Proxy(String pHost, int pPort, String pUser, 
+                                    String pPass)
+    {
+        return new ProxyInfo(ProxyType.SOCKS4, pHost, pPort, pUser, pPass);
+    }
+    
+    public static ProxyInfo forSocks5Proxy(String pHost, int pPort, String pUser, 
+                                    String pPass)
+    {
+        return new ProxyInfo(ProxyType.SOCKS5, pHost, pPort, pUser, pPass);
+    }
+    
+    public static ProxyInfo forNoProxy()
+    {
+        return new ProxyInfo(ProxyType.NONE, null, 0, null, null);
+    }
+    
+    public static ProxyInfo forDefaultProxy()
+    {
+        return new ProxyInfo(ProxyType.NONE, null, 0, null, null);
+    }
+    
+    public ProxyType getProxyType()
+    {
+        return proxyType;
+    }
+    
+    public String getProxyAddress()
+    {
+        return proxyAddress;
+    }
+    
+    public int getProxyPort()
+    {
+        return proxyPort;
+    }
+    
+    public String getProxyUsername()
+    {
+        return proxyUsername;
+    }
+    
+    public String getProxyPassword()
+    {
+        return proxyPassword;
+    }
+    
+    public SocketFactory getSocketFactory()
+    {
+        if(proxyType == ProxyType.NONE)
+        {
+            return new DirectSocketFactory();
+        }
+        else if(proxyType == ProxyType.HTTP)
+        {
+            return new HTTPProxySocketFactory(this);
+        }
+        else if(proxyType == ProxyType.SOCKS4)
+        {
+            return new Socks4ProxySocketFactory(this);
+        }
+        else if(proxyType == ProxyType.SOCKS5)
+        {
+            return new Socks5ProxySocketFactory(this);
+        }
+        else
+        {
+            return null;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/proxy/Socks4ProxySocketFactory.java b/src/org/jivesoftware/smack/proxy/Socks4ProxySocketFactory.java
new file mode 100644
index 0000000..6a32c11
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/Socks4ProxySocketFactory.java
@@ -0,0 +1,216 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.InetAddress;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import javax.net.SocketFactory;
+
+/**
+ * Socket factory for socks4 proxy 
+ *  
+ * @author Atul Aggarwal
+ */
+public class Socks4ProxySocketFactory 
+    extends SocketFactory
+{
+    private ProxyInfo proxy;
+    
+    public Socks4ProxySocketFactory(ProxyInfo proxy)
+    {
+        this.proxy = proxy;
+    }
+
+    public Socket createSocket(String host, int port) 
+        throws IOException, UnknownHostException
+    {
+        return socks4ProxifiedSocket(host,port);
+        
+    }
+
+    public Socket createSocket(String host ,int port, InetAddress localHost,
+                                int localPort)
+        throws IOException, UnknownHostException
+    {
+        return socks4ProxifiedSocket(host,port);
+    }
+
+    public Socket createSocket(InetAddress host, int port)
+        throws IOException
+    {
+        return socks4ProxifiedSocket(host.getHostAddress(),port);
+    }
+
+    public Socket createSocket( InetAddress address, int port, 
+                                InetAddress localAddress, int localPort) 
+        throws IOException
+    {
+        return socks4ProxifiedSocket(address.getHostAddress(),port);
+        
+    }
+    
+    private Socket socks4ProxifiedSocket(String host, int port) 
+        throws IOException
+    {
+        Socket socket = null;
+        InputStream in = null;
+        OutputStream out = null;
+        String proxy_host = proxy.getProxyAddress();
+        int proxy_port = proxy.getProxyPort();
+        String user = proxy.getProxyUsername();
+        String passwd = proxy.getProxyPassword();
+        
+        try
+        {
+            socket=new Socket(proxy_host, proxy_port);    
+            in=socket.getInputStream();
+            out=socket.getOutputStream();
+            socket.setTcpNoDelay(true);
+            
+            byte[] buf=new byte[1024];
+            int index=0;
+
+    /*
+    1) CONNECT
+
+    The client connects to the SOCKS server and sends a CONNECT request when
+    it wants to establish a connection to an application server. The client
+    includes in the request packet the IP address and the port number of the
+    destination host, and userid, in the following format.
+
+           +----+----+----+----+----+----+----+----+----+----+....+----+
+           | VN | CD | DSTPORT |      DSTIP        | USERID       |NULL|
+           +----+----+----+----+----+----+----+----+----+----+....+----+
+    # of bytes:   1    1      2              4           variable       1
+
+    VN is the SOCKS protocol version number and should be 4. CD is the
+    SOCKS command code and should be 1 for CONNECT request. NULL is a byte
+    of all zero bits.
+    */
+
+            index=0;
+            buf[index++]=4;
+            buf[index++]=1;
+
+            buf[index++]=(byte)(port>>>8);
+            buf[index++]=(byte)(port&0xff);
+
+            try
+            {
+                InetAddress addr=InetAddress.getByName(host);
+                byte[] byteAddress = addr.getAddress();
+                for (int i = 0; i < byteAddress.length; i++) 
+                {
+                    buf[index++]=byteAddress[i];
+                }
+            }
+            catch(UnknownHostException uhe)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS4, 
+                    uhe.toString(), uhe);
+            }
+
+            if(user!=null)
+            {
+                System.arraycopy(user.getBytes(), 0, buf, index, user.length());
+                index+=user.length();
+            }
+            buf[index++]=0;
+            out.write(buf, 0, index);
+
+    /*
+    The SOCKS server checks to see whether such a request should be granted
+    based on any combination of source IP address, destination IP address,
+    destination port number, the userid, and information it may obtain by
+    consulting IDENT, cf. RFC 1413.  If the request is granted, the SOCKS
+    server makes a connection to the specified port of the destination host.
+    A reply packet is sent to the client when this connection is established,
+    or when the request is rejected or the operation fails. 
+
+           +----+----+----+----+----+----+----+----+
+           | VN | CD | DSTPORT |      DSTIP        |
+           +----+----+----+----+----+----+----+----+
+    # of bytes:   1    1      2              4
+
+    VN is the version of the reply code and should be 0. CD is the result
+    code with one of the following values:
+
+    90: request granted
+    91: request rejected or failed
+    92: request rejected becasue SOCKS server cannot connect to
+    identd on the client
+    93: request rejected because the client program and identd
+    report different user-ids
+
+    The remaining fields are ignored.
+    */
+
+            int len=6;
+            int s=0;
+            while(s<len)
+            {
+                int i=in.read(buf, s, len-s);
+                if(i<=0)
+                {
+                    throw new ProxyException(ProxyInfo.ProxyType.SOCKS4, 
+                        "stream is closed");
+                }
+                s+=i;
+            }
+            if(buf[0]!=0)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS4, 
+                    "server returns VN "+buf[0]);
+            }
+            if(buf[1]!=90)
+            {
+                try
+                {
+                    socket.close();
+                }
+                catch(Exception eee)
+                {
+                }
+                String message="ProxySOCKS4: server returns CD "+buf[1];
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS4,message);
+            }
+            byte[] temp = new byte[2];
+            in.read(temp, 0, 2);
+            return socket;
+        }
+        catch(RuntimeException e)
+        {
+            throw e;
+        }
+        catch(Exception e)
+        {
+            try
+            {
+                if(socket!=null)socket.close(); 
+            }
+            catch(Exception eee)
+            {
+            }
+            throw new ProxyException(ProxyInfo.ProxyType.SOCKS4, e.toString());
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/proxy/Socks5ProxySocketFactory.java b/src/org/jivesoftware/smack/proxy/Socks5ProxySocketFactory.java
new file mode 100644
index 0000000..23ef623
--- /dev/null
+++ b/src/org/jivesoftware/smack/proxy/Socks5ProxySocketFactory.java
@@ -0,0 +1,375 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.proxy;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.InetAddress;
+import java.net.Socket;
+import java.net.UnknownHostException;
+import javax.net.SocketFactory;
+
+/**
+ * Socket factory for Socks5 proxy
+ * 
+ * @author Atul Aggarwal
+ */
+public class Socks5ProxySocketFactory 
+    extends SocketFactory
+{
+    private ProxyInfo proxy;
+    
+    public Socks5ProxySocketFactory(ProxyInfo proxy)
+    {
+        this.proxy = proxy;
+    }
+
+    public Socket createSocket(String host, int port) 
+        throws IOException, UnknownHostException
+    {
+        return socks5ProxifiedSocket(host,port);
+    }
+
+    public Socket createSocket(String host ,int port, InetAddress localHost,
+                                int localPort)
+        throws IOException, UnknownHostException
+    {
+        
+        return socks5ProxifiedSocket(host,port);
+        
+    }
+
+    public Socket createSocket(InetAddress host, int port)
+        throws IOException
+    {
+        
+        return socks5ProxifiedSocket(host.getHostAddress(),port);
+        
+    }
+
+    public Socket createSocket( InetAddress address, int port, 
+                                InetAddress localAddress, int localPort) 
+        throws IOException
+    {
+        
+        return socks5ProxifiedSocket(address.getHostAddress(),port);
+        
+    }
+    
+    private Socket socks5ProxifiedSocket(String host, int port) 
+        throws IOException
+    {
+        Socket socket = null;
+        InputStream in = null;
+        OutputStream out = null;
+        String proxy_host = proxy.getProxyAddress();
+        int proxy_port = proxy.getProxyPort();
+        String user = proxy.getProxyUsername();
+        String passwd = proxy.getProxyPassword();
+        
+        try
+        {
+            socket=new Socket(proxy_host, proxy_port);    
+            in=socket.getInputStream();
+            out=socket.getOutputStream();
+
+            socket.setTcpNoDelay(true);
+
+            byte[] buf=new byte[1024];
+            int index=0;
+
+/*
+                   +----+----------+----------+
+                   |VER | NMETHODS | METHODS  |
+                   +----+----------+----------+
+                   | 1  |    1     | 1 to 255 |
+                   +----+----------+----------+
+
+   The VER field is set to X'05' for this version of the protocol.  The
+   NMETHODS field contains the number of method identifier octets that
+   appear in the METHODS field.
+
+   The values currently defined for METHOD are:
+
+          o  X'00' NO AUTHENTICATION REQUIRED
+          o  X'01' GSSAPI
+          o  X'02' USERNAME/PASSWORD
+          o  X'03' to X'7F' IANA ASSIGNED
+          o  X'80' to X'FE' RESERVED FOR PRIVATE METHODS
+          o  X'FF' NO ACCEPTABLE METHODS
+*/
+
+            buf[index++]=5;
+
+            buf[index++]=2;
+            buf[index++]=0;           // NO AUTHENTICATION REQUIRED
+            buf[index++]=2;           // USERNAME/PASSWORD
+
+            out.write(buf, 0, index);
+
+/*
+    The server selects from one of the methods given in METHODS, and
+    sends a METHOD selection message:
+
+                         +----+--------+
+                         |VER | METHOD |
+                         +----+--------+
+                         | 1  |   1    |
+                         +----+--------+
+*/
+      //in.read(buf, 0, 2);
+            fill(in, buf, 2);
+
+            boolean check=false;
+            switch((buf[1])&0xff)
+            {
+                case 0:                // NO AUTHENTICATION REQUIRED
+                    check=true;
+                    break;
+                case 2:                // USERNAME/PASSWORD
+                    if(user==null || passwd==null)
+                    {
+                        break;
+                    }
+
+/*
+   Once the SOCKS V5 server has started, and the client has selected the
+   Username/Password Authentication protocol, the Username/Password
+   subnegotiation begins.  This begins with the client producing a
+   Username/Password request:
+
+           +----+------+----------+------+----------+
+           |VER | ULEN |  UNAME   | PLEN |  PASSWD  |
+           +----+------+----------+------+----------+
+           | 1  |  1   | 1 to 255 |  1   | 1 to 255 |
+           +----+------+----------+------+----------+
+
+   The VER field contains the current version of the subnegotiation,
+   which is X'01'. The ULEN field contains the length of the UNAME field
+   that follows. The UNAME field contains the username as known to the
+   source operating system. The PLEN field contains the length of the
+   PASSWD field that follows. The PASSWD field contains the password
+   association with the given UNAME.
+*/
+                    index=0;
+                    buf[index++]=1;
+                    buf[index++]=(byte)(user.length());
+                    System.arraycopy(user.getBytes(), 0, buf, index, 
+                        user.length());
+                    index+=user.length();
+                    buf[index++]=(byte)(passwd.length());
+                    System.arraycopy(passwd.getBytes(), 0, buf, index, 
+                        passwd.length());
+                    index+=passwd.length();
+
+                    out.write(buf, 0, index);
+
+/*
+   The server verifies the supplied UNAME and PASSWD, and sends the
+   following response:
+
+                        +----+--------+
+                        |VER | STATUS |
+                        +----+--------+
+                        | 1  |   1    |
+                        +----+--------+
+
+   A STATUS field of X'00' indicates success. If the server returns a
+   `failure' (STATUS value other than X'00') status, it MUST close the
+   connection.
+*/
+                    //in.read(buf, 0, 2);
+                    fill(in, buf, 2);
+                    if(buf[1]==0)
+                    {
+                        check=true;
+                    }
+                    break;
+                default:
+            }
+
+            if(!check)
+            {
+                try
+                {
+                    socket.close();
+                }
+                catch(Exception eee)
+                {
+                }
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS5,
+                    "fail in SOCKS5 proxy");
+            }
+
+/*
+      The SOCKS request is formed as follows:
+
+        +----+-----+-------+------+----------+----------+
+        |VER | CMD |  RSV  | ATYP | DST.ADDR | DST.PORT |
+        +----+-----+-------+------+----------+----------+
+        | 1  |  1  | X'00' |  1   | Variable |    2     |
+        +----+-----+-------+------+----------+----------+
+
+      Where:
+
+      o  VER    protocol version: X'05'
+      o  CMD
+         o  CONNECT X'01'
+         o  BIND X'02'
+         o  UDP ASSOCIATE X'03'
+      o  RSV    RESERVED
+         o  ATYP   address type of following address
+         o  IP V4 address: X'01'
+         o  DOMAINNAME: X'03'
+         o  IP V6 address: X'04'
+      o  DST.ADDR       desired destination address
+      o  DST.PORT desired destination port in network octet
+         order
+*/
+     
+            index=0;
+            buf[index++]=5;
+            buf[index++]=1;       // CONNECT
+            buf[index++]=0;
+
+            byte[] hostb=host.getBytes();
+            int len=hostb.length;
+            buf[index++]=3;      // DOMAINNAME
+            buf[index++]=(byte)(len);
+            System.arraycopy(hostb, 0, buf, index, len);
+            index+=len;
+            buf[index++]=(byte)(port>>>8);
+            buf[index++]=(byte)(port&0xff);
+
+            out.write(buf, 0, index);
+
+/*
+   The SOCKS request information is sent by the client as soon as it has
+   established a connection to the SOCKS server, and completed the
+   authentication negotiations.  The server evaluates the request, and
+   returns a reply formed as follows:
+
+        +----+-----+-------+------+----------+----------+
+        |VER | REP |  RSV  | ATYP | BND.ADDR | BND.PORT |
+        +----+-----+-------+------+----------+----------+
+        | 1  |  1  | X'00' |  1   | Variable |    2     |
+        +----+-----+-------+------+----------+----------+
+
+   Where:
+
+   o  VER    protocol version: X'05'
+   o  REP    Reply field:
+      o  X'00' succeeded
+      o  X'01' general SOCKS server failure
+      o  X'02' connection not allowed by ruleset
+      o  X'03' Network unreachable
+      o  X'04' Host unreachable
+      o  X'05' Connection refused
+      o  X'06' TTL expired
+      o  X'07' Command not supported
+      o  X'08' Address type not supported
+      o  X'09' to X'FF' unassigned
+    o  RSV    RESERVED
+    o  ATYP   address type of following address
+      o  IP V4 address: X'01'
+      o  DOMAINNAME: X'03'
+      o  IP V6 address: X'04'
+    o  BND.ADDR       server bound address
+    o  BND.PORT       server bound port in network octet order
+*/
+
+      //in.read(buf, 0, 4);
+            fill(in, buf, 4);
+
+            if(buf[1]!=0)
+            {
+                try
+                {
+                    socket.close();
+                }
+                catch(Exception eee)
+                {
+                }
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS5, 
+                    "server returns "+buf[1]);
+            }
+
+            switch(buf[3]&0xff)
+            {
+                case 1:
+                    //in.read(buf, 0, 6);
+                    fill(in, buf, 6);
+                    break;
+                case 3:
+                    //in.read(buf, 0, 1);
+                    fill(in, buf, 1);
+                    //in.read(buf, 0, buf[0]+2);
+                    fill(in, buf, (buf[0]&0xff)+2);
+                    break;
+                case 4:
+                    //in.read(buf, 0, 18);
+                    fill(in, buf, 18);
+                    break;
+                default:
+            }
+            return socket;
+            
+        }
+        catch(RuntimeException e)
+        {
+            throw e;
+        }
+        catch(Exception e)
+        {
+            try
+            {
+                if(socket!=null)
+                {
+                    socket.close(); 
+                }
+            }
+            catch(Exception eee)
+            {
+            }
+            String message="ProxySOCKS5: "+e.toString();
+            if(e instanceof Throwable)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS5,message, 
+                    (Throwable)e);
+            }
+            throw new IOException(message);
+        }
+    }
+    
+    private void fill(InputStream in, byte[] buf, int len) 
+      throws IOException
+    {
+        int s=0;
+        while(s<len)
+        {
+            int i=in.read(buf, s, len-s);
+            if(i<=0)
+            {
+                throw new ProxyException(ProxyInfo.ProxyType.SOCKS5, "stream " +
+                    "is closed");
+            }
+            s+=i;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLAnonymous.java b/src/org/jivesoftware/smack/sasl/SASLAnonymous.java
new file mode 100644
index 0000000..a1b2c88
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLAnonymous.java
@@ -0,0 +1,62 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+
+import java.io.IOException;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+/**
+ * Implementation of the SASL ANONYMOUS mechanism
+ *
+ * @author Jay Kline
+ */
+public class SASLAnonymous extends SASLMechanism {
+
+    public SASLAnonymous(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+    }
+
+    protected String getName() {
+        return "ANONYMOUS";
+    }
+
+    public void authenticate(String username, String host, CallbackHandler cbh) throws IOException {
+        authenticate();
+    }
+
+    public void authenticate(String username, String host, String password) throws IOException {
+        authenticate();
+    }
+
+    protected void authenticate() throws IOException {
+        // Send the authentication to the server
+        getSASLAuthentication().send(new AuthMechanism(getName(), null));
+    }
+
+    public void challengeReceived(String challenge) throws IOException {
+        // Build the challenge response stanza encoding the response text
+        // and send the authentication to the server
+        getSASLAuthentication().send(new Response());
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLCramMD5Mechanism.java b/src/org/jivesoftware/smack/sasl/SASLCramMD5Mechanism.java
new file mode 100644
index 0000000..82d218f
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLCramMD5Mechanism.java
@@ -0,0 +1,38 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+
+/**
+ * Implementation of the SASL CRAM-MD5 mechanism
+ *
+ * @author Jay Kline
+ */
+public class SASLCramMD5Mechanism extends SASLMechanism {
+
+    public SASLCramMD5Mechanism(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+    }
+
+    protected String getName() {
+        return "CRAM-MD5";
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLDigestMD5Mechanism.java b/src/org/jivesoftware/smack/sasl/SASLDigestMD5Mechanism.java
new file mode 100644
index 0000000..7af65fb
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLDigestMD5Mechanism.java
@@ -0,0 +1,38 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+
+/**
+ * Implementation of the SASL DIGEST-MD5 mechanism
+ *
+ * @author Jay Kline
+ */
+public class SASLDigestMD5Mechanism extends SASLMechanism {
+
+    public SASLDigestMD5Mechanism(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+    }
+
+    protected String getName() {
+        return "DIGEST-MD5";
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLExternalMechanism.java b/src/org/jivesoftware/smack/sasl/SASLExternalMechanism.java
new file mode 100644
index 0000000..dff18fb
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLExternalMechanism.java
@@ -0,0 +1,59 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+
+/**
+ * Implementation of the SASL EXTERNAL mechanism.
+ *
+ * To effectively use this mechanism, Java must be configured to properly 
+ * supply a client SSL certificate (of some sort) to the server. It is up
+ * to the implementer to determine how to do this.  Here is one method:
+ *
+ * Create a java keystore with your SSL certificate in it:
+ * keytool -genkey -alias username -dname "cn=username,ou=organizationalUnit,o=organizationaName,l=locality,s=state,c=country"
+ *
+ * Next, set the System Properties:
+ *  <ul>
+ *  <li>javax.net.ssl.keyStore to the location of the keyStore
+ *  <li>javax.net.ssl.keyStorePassword to the password of the keyStore
+ *  <li>javax.net.ssl.trustStore to the location of the trustStore
+ *  <li>javax.net.ssl.trustStorePassword to the the password of the trustStore
+ *  </ul>
+ *
+ * Then, when the server requests or requires the client certificate, java will
+ * simply provide the one in the keyStore.
+ *
+ * Also worth noting is the EXTERNAL mechanism in Smack is not enabled by default.
+ * To enable it, the implementer will need to call SASLAuthentication.supportSASLMechamism("EXTERNAL");
+ *
+ * @author Jay Kline
+ */
+public class SASLExternalMechanism extends SASLMechanism  {
+
+    public SASLExternalMechanism(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+    }
+
+    protected String getName() {
+        return "EXTERNAL";
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLFacebookConnect.java b/src/org/jivesoftware/smack/sasl/SASLFacebookConnect.java
new file mode 100644
index 0000000..3126d83
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLFacebookConnect.java
@@ -0,0 +1,201 @@
+package org.jivesoftware.smack.sasl;
+
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.net.URLEncoder;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.GregorianCalendar;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import de.measite.smack.Sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.sasl.SASLMechanism;
+import org.jivesoftware.smack.util.Base64;
+
+/**
+ * This class is originally from http://code.google.com/p/fbgc/source/browse/trunk/daemon/src/main/java/org/albino/mechanisms/FacebookConnectSASLMechanism.java
+ * I just adapted to match the SMACK package scheme and 
+ */
+public class SASLFacebookConnect extends SASLMechanism {
+
+        private String sessionKey = "";
+        private String sessionSecret = "";
+        private String apiKey = "";
+        
+        static{
+        	SASLAuthentication.registerSASLMechanism("X-FACEBOOK-PLATFORM",
+                    SASLFacebookConnect.class);
+        	SASLAuthentication.supportSASLMechanism("X-FACEBOOK-PLATFORM", 0);
+        }
+        
+        public SASLFacebookConnect(SASLAuthentication saslAuthentication) {
+                super(saslAuthentication);
+        }
+
+        // protected void authenticate() throws IOException, XMPPException {
+        // String[] mechanisms = { getName() };
+        // Map<String, String> props = new HashMap<String, String>();
+        // sc = Sasl.createSaslClient(mechanisms, null, "xmpp", hostname, props,
+        // this);
+        //
+        // super.authenticate();
+        // }
+
+        protected void authenticate() throws IOException, XMPPException {
+                final StringBuilder stanza = new StringBuilder();
+                stanza.append("<auth mechanism=\"").append(getName());
+                stanza.append("\" xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+                stanza.append("</auth>");
+
+                // Send the authentication to the server
+                getSASLAuthentication().send(new Packet(){
+
+					@Override
+					public String toXML() {
+						return stanza.toString();
+					}    	
+                	
+                });
+        }
+
+        public void authenticate(String apiKeyAndSessionKey, String host, String sessionSecret)
+                        throws IOException, XMPPException {
+
+                if(apiKeyAndSessionKey==null || sessionSecret==null)
+                        throw new IllegalStateException("Invalid parameters!");
+                
+                String[] keyArray = apiKeyAndSessionKey.split("\\|");
+                
+                if(keyArray==null || keyArray.length != 2)
+                        throw new IllegalStateException("Api key or session key is not present!");
+                
+                this.apiKey = keyArray[0];
+                this.sessionKey = keyArray[1];
+                this.sessionSecret = sessionSecret;
+                
+                this.authenticationId = sessionKey;
+                this.password = sessionSecret;
+                this.hostname = host;
+
+                String[] mechanisms = { "DIGEST-MD5" };
+                Map<String, String> props = new HashMap<String, String>();
+                sc = Sasl.createSaslClient(mechanisms, null, "xmpp", host, props, this);
+                authenticate();
+        }
+
+        public void authenticate(String username, String host, CallbackHandler cbh)
+                        throws IOException, XMPPException {
+                String[] mechanisms = { "DIGEST-MD5" };
+                Map<String, String> props = new HashMap<String, String>();
+                sc = Sasl.createSaslClient(mechanisms, null, "xmpp", host, props, cbh);
+                authenticate();
+        }
+
+        protected String getName() {
+                return "X-FACEBOOK-PLATFORM";
+        }
+
+        public void challengeReceived(String challenge) throws IOException {
+                // Build the challenge response stanza encoding the response text
+                final StringBuilder stanza = new StringBuilder();
+
+                byte response[] = null;
+                if (challenge != null) {
+                        String decodedResponse = new String(Base64.decode(challenge));
+                        Map<String, String> parameters = getQueryMap(decodedResponse);
+
+                        String version = "1.0";
+                        String nonce = parameters.get("nonce");
+                        String method = parameters.get("method");
+                        
+                        Long callId = new GregorianCalendar().getTimeInMillis()/1000;
+                        
+                        String sig = "api_key="+apiKey
+                                                        +"call_id="+callId
+                                                        +"method="+method
+                                                        +"nonce="+nonce
+                                                        +"session_key="+sessionKey
+                                                        +"v="+version
+                                                        +sessionSecret;
+                        
+                        try {
+                                sig = MD5(sig);
+                        } catch (NoSuchAlgorithmException e) {
+                                throw new IllegalStateException(e);
+                        }
+                        
+                        String composedResponse = "api_key="+apiKey+"&"
+                                                                                +"call_id="+callId+"&"
+                                                                                +"method="+method+"&"
+                                                                                +"nonce="+nonce+"&"
+                                                                                +"session_key="+sessionKey+"&"
+                                                                                +"v="+version+"&"
+                                                                                +"sig="+sig;
+                        
+                        response = composedResponse.getBytes();
+                }
+
+                String authenticationText="";
+
+                if (response != null) {
+                        authenticationText = Base64.encodeBytes(response, Base64.DONT_BREAK_LINES);
+                }
+
+                stanza.append("<response xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+                stanza.append(authenticationText);
+                stanza.append("</response>");
+
+                // Send the authentication to the server
+                getSASLAuthentication().send(new Packet(){
+
+					@Override
+					public String toXML() {
+						return stanza.toString();
+					}
+                	
+                });
+        }
+
+        private Map<String, String> getQueryMap(String query) {
+                String[] params = query.split("&");
+                Map<String, String> map = new HashMap<String, String>();
+                for (String param : params) {
+                        String name = param.split("=")[0];
+                        String value = param.split("=")[1];
+                        map.put(name, value);
+                }
+                return map;
+        }
+        
+    private String convertToHex(byte[] data) {
+        StringBuffer buf = new StringBuffer();
+        for (int i = 0; i < data.length; i++) {
+            int halfbyte = (data[i] >>> 4) & 0x0F;
+            int two_halfs = 0;
+            do {
+                if ((0 <= halfbyte) && (halfbyte <= 9))
+                    buf.append((char) ('0' + halfbyte));
+                else
+                    buf.append((char) ('a' + (halfbyte - 10)));
+                halfbyte = data[i] & 0x0F;
+            } while(two_halfs++ < 1);
+        }
+        return buf.toString();
+    }
+ 
+    public String MD5(String text) throws NoSuchAlgorithmException, UnsupportedEncodingException  {
+        MessageDigest md;
+        md = MessageDigest.getInstance("MD5");
+        byte[] md5hash = new byte[32];
+        md.update(text.getBytes("iso-8859-1"), 0, text.length());
+        md5hash = md.digest();
+        return convertToHex(md5hash);
+    }
+}
+
diff --git a/src/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java b/src/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java
new file mode 100644
index 0000000..e8a4967
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLGSSAPIMechanism.java
@@ -0,0 +1,89 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+import org.jivesoftware.smack.XMPPException;
+
+import java.io.IOException;
+import java.util.Map;
+import java.util.HashMap;
+import de.measite.smack.Sasl;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+
+/**
+ * Implementation of the SASL GSSAPI mechanism
+ *
+ * @author Jay Kline
+ */
+public class SASLGSSAPIMechanism extends SASLMechanism {
+
+    public SASLGSSAPIMechanism(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+
+        System.setProperty("javax.security.auth.useSubjectCredsOnly","false");
+        System.setProperty("java.security.auth.login.config","gss.conf");
+
+    }
+
+    protected String getName() {
+        return "GSSAPI";
+    }
+
+    /**
+     * Builds and sends the <tt>auth</tt> stanza to the server.
+     * This overrides from the abstract class because the initial token
+     * needed for GSSAPI is binary, and not safe to put in a string, thus
+     * getAuthenticationText() cannot be used.
+     *
+     * @param username the username of the user being authenticated.
+     * @param host     the hostname where the user account resides.
+     * @param cbh      the CallbackHandler (not used with GSSAPI)
+     * @throws IOException If a network error occures while authenticating.
+     */
+    public void authenticate(String username, String host, CallbackHandler cbh) throws IOException, XMPPException {
+        String[] mechanisms = { getName() };
+        Map<String,String> props = new HashMap<String,String>();
+        props.put(Sasl.SERVER_AUTH,"TRUE");
+        sc = Sasl.createSaslClient(mechanisms, username, "xmpp", host, props, cbh);
+        authenticate();
+    }
+
+    /**
+     * Builds and sends the <tt>auth</tt> stanza to the server.
+     * This overrides from the abstract class because the initial token
+     * needed for GSSAPI is binary, and not safe to put in a string, thus
+     * getAuthenticationText() cannot be used.
+     *
+     * @param username the username of the user being authenticated.
+     * @param host     the hostname where the user account resides.
+     * @param password the password of the user (ignored for GSSAPI)
+     * @throws IOException If a network error occures while authenticating.
+     */
+    public void authenticate(String username, String host, String password) throws IOException, XMPPException {
+        String[] mechanisms = { getName() };
+        Map<String,String> props = new HashMap<String, String>();
+        props.put(Sasl.SERVER_AUTH,"TRUE");
+        sc = Sasl.createSaslClient(mechanisms, username, "xmpp", host, props, this);
+        authenticate();
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLMechanism.java b/src/org/jivesoftware/smack/sasl/SASLMechanism.java
new file mode 100644
index 0000000..3aeba86
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLMechanism.java
@@ -0,0 +1,323 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.SASLAuthentication;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.io.IOException;
+import java.util.Map;
+import java.util.HashMap;
+import org.apache.harmony.javax.security.auth.callback.CallbackHandler;
+import org.apache.harmony.javax.security.auth.callback.UnsupportedCallbackException;
+import org.apache.harmony.javax.security.auth.callback.Callback;
+import org.apache.harmony.javax.security.auth.callback.NameCallback;
+import org.apache.harmony.javax.security.auth.callback.PasswordCallback;
+import org.apache.harmony.javax.security.sasl.RealmCallback;
+import org.apache.harmony.javax.security.sasl.RealmChoiceCallback;
+import de.measite.smack.Sasl;
+import org.apache.harmony.javax.security.sasl.SaslClient;
+import org.apache.harmony.javax.security.sasl.SaslException;
+
+/**
+ * Base class for SASL mechanisms. Subclasses must implement these methods:
+ * <ul>
+ *  <li>{@link #getName()} -- returns the common name of the SASL mechanism.</li>
+ * </ul>
+ * Subclasses will likely want to implement their own versions of these mthods:
+ *  <li>{@link #authenticate(String, String, String)} -- Initiate authentication stanza using the
+ *  deprecated method.</li>
+ *  <li>{@link #authenticate(String, String, CallbackHandler)} -- Initiate authentication stanza
+ *  using the CallbackHandler method.</li>
+ *  <li>{@link #challengeReceived(String)} -- Handle a challenge from the server.</li>
+ * </ul>
+ *
+ * @author Jay Kline
+ */
+public abstract class SASLMechanism implements CallbackHandler {
+
+    private SASLAuthentication saslAuthentication;
+    protected SaslClient sc;
+    protected String authenticationId;
+    protected String password;
+    protected String hostname;
+
+
+    public SASLMechanism(SASLAuthentication saslAuthentication) {
+        this.saslAuthentication = saslAuthentication;
+    }
+
+    /**
+     * Builds and sends the <tt>auth</tt> stanza to the server. Note that this method of
+     * authentication is not recommended, since it is very inflexable.  Use
+     * {@link #authenticate(String, String, CallbackHandler)} whenever possible.
+     *
+     * @param username the username of the user being authenticated.
+     * @param host     the hostname where the user account resides.
+     * @param password the password for this account.
+     * @throws IOException If a network error occurs while authenticating.
+     * @throws XMPPException If a protocol error occurs or the user is not authenticated.
+     */
+    public void authenticate(String username, String host, String password) throws IOException, XMPPException {
+        //Since we were not provided with a CallbackHandler, we will use our own with the given
+        //information
+
+        //Set the authenticationID as the username, since they must be the same in this case.
+        this.authenticationId = username;
+        this.password = password;
+        this.hostname = host;
+
+        String[] mechanisms = { getName() };
+        Map<String,String> props = new HashMap<String,String>();
+        sc = Sasl.createSaslClient(mechanisms, username, "xmpp", host, props, this);
+        authenticate();
+    }
+
+    /**
+     * Builds and sends the <tt>auth</tt> stanza to the server. The callback handler will handle
+     * any additional information, such as the authentication ID or realm, if it is needed.
+     *
+     * @param username the username of the user being authenticated.
+     * @param host     the hostname where the user account resides.
+     * @param cbh      the CallbackHandler to obtain user information.
+     * @throws IOException If a network error occures while authenticating.
+     * @throws XMPPException If a protocol error occurs or the user is not authenticated.
+     */
+    public void authenticate(String username, String host, CallbackHandler cbh) throws IOException, XMPPException {
+        String[] mechanisms = { getName() };
+        Map<String,String> props = new HashMap<String,String>();
+        sc = Sasl.createSaslClient(mechanisms, username, "xmpp", host, props, cbh);
+        authenticate();
+    }
+
+    protected void authenticate() throws IOException, XMPPException {
+        String authenticationText = null;
+        try {
+            if(sc.hasInitialResponse()) {
+                byte[] response = sc.evaluateChallenge(new byte[0]);
+                authenticationText = StringUtils.encodeBase64(response, false);
+            }
+        } catch (SaslException e) {
+            throw new XMPPException("SASL authentication failed", e);
+        }
+
+        // Send the authentication to the server
+        getSASLAuthentication().send(new AuthMechanism(getName(), authenticationText));
+    }
+
+
+    /**
+     * The server is challenging the SASL mechanism for the stanza he just sent. Send a
+     * response to the server's challenge.
+     *
+     * @param challenge a base64 encoded string representing the challenge.
+     * @throws IOException if an exception sending the response occurs.
+     */
+    public void challengeReceived(String challenge) throws IOException {
+        byte response[];
+        if(challenge != null) {
+            response = sc.evaluateChallenge(StringUtils.decodeBase64(challenge));
+        } else {
+            response = sc.evaluateChallenge(new byte[0]);
+        }
+
+        Packet responseStanza;
+        if (response == null) {
+            responseStanza = new Response();
+        }
+        else {
+            responseStanza = new Response(StringUtils.encodeBase64(response, false));
+        }
+
+        // Send the authentication to the server
+        getSASLAuthentication().send(responseStanza);
+    }
+
+    /**
+     * Returns the common name of the SASL mechanism. E.g.: PLAIN, DIGEST-MD5 or GSSAPI.
+     *
+     * @return the common name of the SASL mechanism.
+     */
+    protected abstract String getName();
+
+
+    protected SASLAuthentication getSASLAuthentication() {
+        return saslAuthentication;
+    }
+
+    /**
+     * 
+     */
+    public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
+        for (int i = 0; i < callbacks.length; i++) {
+            if (callbacks[i] instanceof NameCallback) {
+                NameCallback ncb = (NameCallback)callbacks[i];
+                ncb.setName(authenticationId);
+            } else if(callbacks[i] instanceof PasswordCallback) {
+                PasswordCallback pcb = (PasswordCallback)callbacks[i];
+                pcb.setPassword(password.toCharArray());
+            } else if(callbacks[i] instanceof RealmCallback) {
+                RealmCallback rcb = (RealmCallback)callbacks[i];
+                rcb.setText(hostname);
+            } else if(callbacks[i] instanceof RealmChoiceCallback){
+                //unused
+                //RealmChoiceCallback rccb = (RealmChoiceCallback)callbacks[i];
+            } else {
+               throw new UnsupportedCallbackException(callbacks[i]);
+            }
+         }
+    }
+
+    /**
+     * Initiating SASL authentication by select a mechanism.
+     */
+    public class AuthMechanism extends Packet {
+        final private String name;
+        final private String authenticationText;
+
+        public AuthMechanism(String name, String authenticationText) {
+            if (name == null) {
+                throw new NullPointerException("SASL mechanism name shouldn't be null.");
+            }
+            this.name = name;
+            this.authenticationText = authenticationText;
+        }
+
+        public String toXML() {
+            StringBuilder stanza = new StringBuilder();
+            stanza.append("<auth mechanism=\"").append(name);
+            stanza.append("\" xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+            if (authenticationText != null &&
+                    authenticationText.trim().length() > 0) {
+                stanza.append(authenticationText);
+            }
+            stanza.append("</auth>");
+            return stanza.toString();
+        }
+    }
+
+    /**
+     * A SASL challenge stanza.
+     */
+    public static class Challenge extends Packet {
+        final private String data;
+
+        public Challenge(String data) {
+            this.data = data;
+        }
+
+        public String toXML() {
+            StringBuilder stanza = new StringBuilder();
+            stanza.append("<challenge xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+            if (data != null &&
+                    data.trim().length() > 0) {
+                stanza.append(data);
+            }
+            stanza.append("</challenge>");
+            return stanza.toString();
+        }
+    }
+
+    /**
+     * A SASL response stanza.
+     */
+    public class Response extends Packet {
+        final private String authenticationText;
+
+        public Response() {
+            authenticationText = null;
+        }
+
+        public Response(String authenticationText) {
+            if (authenticationText == null || authenticationText.trim().length() == 0) {
+                this.authenticationText = null;
+            }
+            else {
+                this.authenticationText = authenticationText;
+            }
+        }
+
+        public String toXML() {
+            StringBuilder stanza = new StringBuilder();
+            stanza.append("<response xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+            if (authenticationText != null) {
+                stanza.append(authenticationText);
+            }
+            stanza.append("</response>");
+            return stanza.toString();
+        }
+    }
+
+    /**
+     * A SASL success stanza.
+     */
+    public static class Success extends Packet {
+        final private String data;
+
+        public Success(String data) {
+            this.data = data;
+        }
+
+        public String toXML() {
+            StringBuilder stanza = new StringBuilder();
+            stanza.append("<success xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+            if (data != null &&
+                    data.trim().length() > 0) {
+                stanza.append(data);
+            }
+            stanza.append("</success>");
+            return stanza.toString();
+        }
+    }
+
+    /**
+     * A SASL failure stanza.
+     */
+    public static class Failure extends Packet {
+        final private String condition;
+
+        public Failure(String condition) {
+            this.condition = condition;
+        }
+
+        /**
+         * Get the SASL related error condition.
+         * 
+         * @return the SASL related error condition.
+         */
+        public String getCondition() {
+            return condition;
+        }
+
+        public String toXML() {
+            StringBuilder stanza = new StringBuilder();
+            stanza.append("<failure xmlns=\"urn:ietf:params:xml:ns:xmpp-sasl\">");
+            if (condition != null &&
+                    condition.trim().length() > 0) {
+                stanza.append("<").append(condition).append("/>");
+            }
+            stanza.append("</failure>");
+            return stanza.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/SASLPlainMechanism.java b/src/org/jivesoftware/smack/sasl/SASLPlainMechanism.java
new file mode 100644
index 0000000..cd973eb
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/SASLPlainMechanism.java
@@ -0,0 +1,34 @@
+/**
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.sasl;
+
+import org.jivesoftware.smack.SASLAuthentication;
+
+/**
+ * Implementation of the SASL PLAIN mechanism
+ *
+ * @author Jay Kline
+ */
+public class SASLPlainMechanism extends SASLMechanism {
+
+    public SASLPlainMechanism(SASLAuthentication saslAuthentication) {
+        super(saslAuthentication);
+    }
+
+    protected String getName() {
+        return "PLAIN";
+    }
+}
diff --git a/src/org/jivesoftware/smack/sasl/package.html b/src/org/jivesoftware/smack/sasl/package.html
new file mode 100644
index 0000000..1e8cfb7
--- /dev/null
+++ b/src/org/jivesoftware/smack/sasl/package.html
@@ -0,0 +1 @@
+<body>SASL Mechanisms.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/util/Base32Encoder.java b/src/org/jivesoftware/smack/util/Base32Encoder.java
new file mode 100644
index 0000000..0a4ea21
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/Base32Encoder.java
@@ -0,0 +1,184 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util;
+
+
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+
+/**
+ * Base32 string encoding is useful for when filenames case-insensitive filesystems are encoded.
+ * Base32 representation takes roughly 20% more space then Base64.
+ * 
+ * @author Florian Schmaus
+ * Based on code by Brian Wellington (bwelling@xbill.org)
+ * @see <a href="http://en.wikipedia.org/wiki/Base32">Base32 Wikipedia entry<a>
+ *
+ */
+public class Base32Encoder implements StringEncoder {
+
+    private static Base32Encoder instance = new Base32Encoder();
+    private static final String ALPHABET = "ABCDEFGHIJKLMNOPQRSTUVWXYZ2345678";
+
+    private Base32Encoder() {
+        // Use getInstance()
+    }
+
+    public static Base32Encoder getInstance() {
+        return instance;
+    }
+
+    @Override
+    public String decode(String str) {
+        ByteArrayOutputStream bs = new ByteArrayOutputStream();
+        byte[] raw = str.getBytes();
+        for (int i = 0; i < raw.length; i++) {
+            char c = (char) raw[i];
+            if (!Character.isWhitespace(c)) {
+                c = Character.toUpperCase(c);
+                bs.write((byte) c);
+            }
+        }
+
+        while (bs.size() % 8 != 0)
+            bs.write('8');
+
+        byte[] in = bs.toByteArray();
+
+        bs.reset();
+        DataOutputStream ds = new DataOutputStream(bs);
+
+        for (int i = 0; i < in.length / 8; i++) {
+            short[] s = new short[8];
+            int[] t = new int[5];
+
+            int padlen = 8;
+            for (int j = 0; j < 8; j++) {
+                char c = (char) in[i * 8 + j];
+                if (c == '8')
+                    break;
+                s[j] = (short) ALPHABET.indexOf(in[i * 8 + j]);
+                if (s[j] < 0)
+                    return null;
+                padlen--;
+            }
+            int blocklen = paddingToLen(padlen);
+            if (blocklen < 0)
+                return null;
+
+            // all 5 bits of 1st, high 3 (of 5) of 2nd
+            t[0] = (s[0] << 3) | s[1] >> 2;
+            // lower 2 of 2nd, all 5 of 3rd, high 1 of 4th
+            t[1] = ((s[1] & 0x03) << 6) | (s[2] << 1) | (s[3] >> 4);
+            // lower 4 of 4th, high 4 of 5th
+            t[2] = ((s[3] & 0x0F) << 4) | ((s[4] >> 1) & 0x0F);
+            // lower 1 of 5th, all 5 of 6th, high 2 of 7th
+            t[3] = (s[4] << 7) | (s[5] << 2) | (s[6] >> 3);
+            // lower 3 of 7th, all of 8th
+            t[4] = ((s[6] & 0x07) << 5) | s[7];
+
+            try {
+                for (int j = 0; j < blocklen; j++)
+                    ds.writeByte((byte) (t[j] & 0xFF));
+            } catch (IOException e) {
+            }
+        }
+
+        return new String(bs.toByteArray());
+    }
+
+    @Override
+    public String encode(String str) {
+        byte[] b = str.getBytes();
+        ByteArrayOutputStream os = new ByteArrayOutputStream();
+
+        for (int i = 0; i < (b.length + 4) / 5; i++) {
+            short s[] = new short[5];
+            int t[] = new int[8];
+
+            int blocklen = 5;
+            for (int j = 0; j < 5; j++) {
+                if ((i * 5 + j) < b.length)
+                    s[j] = (short) (b[i * 5 + j] & 0xFF);
+                else {
+                    s[j] = 0;
+                    blocklen--;
+                }
+            }
+            int padlen = lenToPadding(blocklen);
+
+            // convert the 5 byte block into 8 characters (values 0-31).
+
+            // upper 5 bits from first byte
+            t[0] = (byte) ((s[0] >> 3) & 0x1F);
+            // lower 3 bits from 1st byte, upper 2 bits from 2nd.
+            t[1] = (byte) (((s[0] & 0x07) << 2) | ((s[1] >> 6) & 0x03));
+            // bits 5-1 from 2nd.
+            t[2] = (byte) ((s[1] >> 1) & 0x1F);
+            // lower 1 bit from 2nd, upper 4 from 3rd
+            t[3] = (byte) (((s[1] & 0x01) << 4) | ((s[2] >> 4) & 0x0F));
+            // lower 4 from 3rd, upper 1 from 4th.
+            t[4] = (byte) (((s[2] & 0x0F) << 1) | ((s[3] >> 7) & 0x01));
+            // bits 6-2 from 4th
+            t[5] = (byte) ((s[3] >> 2) & 0x1F);
+            // lower 2 from 4th, upper 3 from 5th;
+            t[6] = (byte) (((s[3] & 0x03) << 3) | ((s[4] >> 5) & 0x07));
+            // lower 5 from 5th;
+            t[7] = (byte) (s[4] & 0x1F);
+
+            // write out the actual characters.
+            for (int j = 0; j < t.length - padlen; j++) {
+                char c = ALPHABET.charAt(t[j]);
+                os.write(c);
+            }
+        }
+        return new String(os.toByteArray());
+    }
+
+    private static int lenToPadding(int blocklen) {
+        switch (blocklen) {
+        case 1:
+            return 6;
+        case 2:
+            return 4;
+        case 3:
+            return 3;
+        case 4:
+            return 1;
+        case 5:
+            return 0;
+        default:
+            return -1;
+        }
+    }
+
+    private static int paddingToLen(int padlen) {
+        switch (padlen) {
+        case 6:
+            return 1;
+        case 4:
+            return 2;
+        case 3:
+            return 3;
+        case 1:
+            return 4;
+        case 0:
+            return 5;
+        default:
+            return -1;
+        }
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/Base64.java b/src/org/jivesoftware/smack/util/Base64.java
new file mode 100644
index 0000000..ba6eb37
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/Base64.java
@@ -0,0 +1,1689 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ */
+package org.jivesoftware.smack.util;
+
+/**
+ * <p>Encodes and decodes to and from Base64 notation.</p>
+ * This code was obtained from <a href="http://iharder.net/base64">http://iharder.net/base64</a></p>
+ *
+ *
+ * @author Robert Harder
+ * @author rob@iharder.net
+ * @version 2.2.1
+ */
+public class Base64
+{
+
+/* ********  P U B L I C   F I E L D S  ******** */
+
+
+    /** No options specified. Value is zero. */
+    public final static int NO_OPTIONS = 0;
+
+    /** Specify encoding. */
+    public final static int ENCODE = 1;
+
+
+    /** Specify decoding. */
+    public final static int DECODE = 0;
+
+
+    /** Specify that data should be gzip-compressed. */
+    public final static int GZIP = 2;
+
+
+    /** Don't break lines when encoding (violates strict Base64 specification) */
+    public final static int DONT_BREAK_LINES = 8;
+
+	/**
+	 * Encode using Base64-like encoding that is URL- and Filename-safe as described
+	 * in Section 4 of RFC3548:
+	 * <a href="http://www.faqs.org/rfcs/rfc3548.html">http://www.faqs.org/rfcs/rfc3548.html</a>.
+	 * It is important to note that data encoded this way is <em>not</em> officially valid Base64,
+	 * or at the very least should not be called Base64 without also specifying that is
+	 * was encoded using the URL- and Filename-safe dialect.
+	 */
+	 public final static int URL_SAFE = 16;
+
+
+	 /**
+	  * Encode using the special "ordered" dialect of Base64 described here:
+	  * <a href="http://www.faqs.org/qa/rfcc-1940.html">http://www.faqs.org/qa/rfcc-1940.html</a>.
+	  */
+	 public final static int ORDERED = 32;
+
+
+/* ********  P R I V A T E   F I E L D S  ******** */
+
+
+    /** Maximum line length (76) of Base64 output. */
+    private final static int MAX_LINE_LENGTH = 76;
+
+
+    /** The equals sign (=) as a byte. */
+    private final static byte EQUALS_SIGN = (byte)'=';
+
+
+    /** The new line character (\n) as a byte. */
+    private final static byte NEW_LINE = (byte)'\n';
+
+
+    /** Preferred encoding. */
+    private final static String PREFERRED_ENCODING = "UTF-8";
+
+
+    // I think I end up not using the BAD_ENCODING indicator.
+    //private final static byte BAD_ENCODING    = -9; // Indicates error in encoding
+    private final static byte WHITE_SPACE_ENC = -5; // Indicates white space in encoding
+    private final static byte EQUALS_SIGN_ENC = -1; // Indicates equals sign in encoding
+
+
+/* ********  S T A N D A R D   B A S E 6 4   A L P H A B E T  ******** */
+
+    /** The 64 valid Base64 values. */
+    //private final static byte[] ALPHABET;
+	/* Host platform me be something funny like EBCDIC, so we hardcode these values. */
+	private final static byte[] _STANDARD_ALPHABET =
+    {
+        (byte)'A', (byte)'B', (byte)'C', (byte)'D', (byte)'E', (byte)'F', (byte)'G',
+        (byte)'H', (byte)'I', (byte)'J', (byte)'K', (byte)'L', (byte)'M', (byte)'N',
+        (byte)'O', (byte)'P', (byte)'Q', (byte)'R', (byte)'S', (byte)'T', (byte)'U',
+        (byte)'V', (byte)'W', (byte)'X', (byte)'Y', (byte)'Z',
+        (byte)'a', (byte)'b', (byte)'c', (byte)'d', (byte)'e', (byte)'f', (byte)'g',
+        (byte)'h', (byte)'i', (byte)'j', (byte)'k', (byte)'l', (byte)'m', (byte)'n',
+        (byte)'o', (byte)'p', (byte)'q', (byte)'r', (byte)'s', (byte)'t', (byte)'u',
+        (byte)'v', (byte)'w', (byte)'x', (byte)'y', (byte)'z',
+        (byte)'0', (byte)'1', (byte)'2', (byte)'3', (byte)'4', (byte)'5',
+        (byte)'6', (byte)'7', (byte)'8', (byte)'9', (byte)'+', (byte)'/'
+    };
+
+
+    /**
+     * Translates a Base64 value to either its 6-bit reconstruction value
+     * or a negative number indicating some other meaning.
+     **/
+    private final static byte[] _STANDARD_DECODABET =
+    {
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,                 // Decimal  0 -  8
+        -5,-5,                                      // Whitespace: Tab and Linefeed
+        -9,-9,                                      // Decimal 11 - 12
+        -5,                                         // Whitespace: Carriage Return
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 14 - 26
+        -9,-9,-9,-9,-9,                             // Decimal 27 - 31
+        -5,                                         // Whitespace: Space
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,              // Decimal 33 - 42
+        62,                                         // Plus sign at decimal 43
+        -9,-9,-9,                                   // Decimal 44 - 46
+        63,                                         // Slash at decimal 47
+        52,53,54,55,56,57,58,59,60,61,              // Numbers zero through nine
+        -9,-9,-9,                                   // Decimal 58 - 60
+        -1,                                         // Equals sign at decimal 61
+        -9,-9,-9,                                      // Decimal 62 - 64
+        0,1,2,3,4,5,6,7,8,9,10,11,12,13,            // Letters 'A' through 'N'
+        14,15,16,17,18,19,20,21,22,23,24,25,        // Letters 'O' through 'Z'
+        -9,-9,-9,-9,-9,-9,                          // Decimal 91 - 96
+        26,27,28,29,30,31,32,33,34,35,36,37,38,     // Letters 'a' through 'm'
+        39,40,41,42,43,44,45,46,47,48,49,50,51,     // Letters 'n' through 'z'
+        -9,-9,-9,-9                                 // Decimal 123 - 126
+        /*,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 127 - 139
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 140 - 152
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 153 - 165
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 166 - 178
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 179 - 191
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 192 - 204
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 205 - 217
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 218 - 230
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 231 - 243
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9         // Decimal 244 - 255 */
+    };
+
+
+/* ********  U R L   S A F E   B A S E 6 4   A L P H A B E T  ******** */
+
+	/**
+	 * Used in the URL- and Filename-safe dialect described in Section 4 of RFC3548:
+	 * <a href="http://www.faqs.org/rfcs/rfc3548.html">http://www.faqs.org/rfcs/rfc3548.html</a>.
+	 * Notice that the last two bytes become "hyphen" and "underscore" instead of "plus" and "slash."
+	 */
+    private final static byte[] _URL_SAFE_ALPHABET =
+    {
+      (byte)'A', (byte)'B', (byte)'C', (byte)'D', (byte)'E', (byte)'F', (byte)'G',
+      (byte)'H', (byte)'I', (byte)'J', (byte)'K', (byte)'L', (byte)'M', (byte)'N',
+      (byte)'O', (byte)'P', (byte)'Q', (byte)'R', (byte)'S', (byte)'T', (byte)'U',
+      (byte)'V', (byte)'W', (byte)'X', (byte)'Y', (byte)'Z',
+      (byte)'a', (byte)'b', (byte)'c', (byte)'d', (byte)'e', (byte)'f', (byte)'g',
+      (byte)'h', (byte)'i', (byte)'j', (byte)'k', (byte)'l', (byte)'m', (byte)'n',
+      (byte)'o', (byte)'p', (byte)'q', (byte)'r', (byte)'s', (byte)'t', (byte)'u',
+      (byte)'v', (byte)'w', (byte)'x', (byte)'y', (byte)'z',
+      (byte)'0', (byte)'1', (byte)'2', (byte)'3', (byte)'4', (byte)'5',
+      (byte)'6', (byte)'7', (byte)'8', (byte)'9', (byte)'-', (byte)'_'
+    };
+
+	/**
+	 * Used in decoding URL- and Filename-safe dialects of Base64.
+	 */
+    private final static byte[] _URL_SAFE_DECODABET =
+    {
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,                 // Decimal  0 -  8
+      -5,-5,                                      // Whitespace: Tab and Linefeed
+      -9,-9,                                      // Decimal 11 - 12
+      -5,                                         // Whitespace: Carriage Return
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 14 - 26
+      -9,-9,-9,-9,-9,                             // Decimal 27 - 31
+      -5,                                         // Whitespace: Space
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,              // Decimal 33 - 42
+      -9,                                         // Plus sign at decimal 43
+      -9,                                         // Decimal 44
+      62,                                         // Minus sign at decimal 45
+      -9,                                         // Decimal 46
+      -9,                                         // Slash at decimal 47
+      52,53,54,55,56,57,58,59,60,61,              // Numbers zero through nine
+      -9,-9,-9,                                   // Decimal 58 - 60
+      -1,                                         // Equals sign at decimal 61
+      -9,-9,-9,                                   // Decimal 62 - 64
+      0,1,2,3,4,5,6,7,8,9,10,11,12,13,            // Letters 'A' through 'N'
+      14,15,16,17,18,19,20,21,22,23,24,25,        // Letters 'O' through 'Z'
+      -9,-9,-9,-9,                                // Decimal 91 - 94
+      63,                                         // Underscore at decimal 95
+      -9,                                         // Decimal 96
+      26,27,28,29,30,31,32,33,34,35,36,37,38,     // Letters 'a' through 'm'
+      39,40,41,42,43,44,45,46,47,48,49,50,51,     // Letters 'n' through 'z'
+      -9,-9,-9,-9                                 // Decimal 123 - 126
+      /*,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 127 - 139
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 140 - 152
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 153 - 165
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 166 - 178
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 179 - 191
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 192 - 204
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 205 - 217
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 218 - 230
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 231 - 243
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9         // Decimal 244 - 255 */
+    };
+
+
+
+/* ********  O R D E R E D   B A S E 6 4   A L P H A B E T  ******** */
+
+	/**
+	 * I don't get the point of this technique, but it is described here:
+	 * <a href="http://www.faqs.org/qa/rfcc-1940.html">http://www.faqs.org/qa/rfcc-1940.html</a>.
+	 */
+    private final static byte[] _ORDERED_ALPHABET =
+    {
+      (byte)'-',
+      (byte)'0', (byte)'1', (byte)'2', (byte)'3', (byte)'4',
+      (byte)'5', (byte)'6', (byte)'7', (byte)'8', (byte)'9',
+      (byte)'A', (byte)'B', (byte)'C', (byte)'D', (byte)'E', (byte)'F', (byte)'G',
+      (byte)'H', (byte)'I', (byte)'J', (byte)'K', (byte)'L', (byte)'M', (byte)'N',
+      (byte)'O', (byte)'P', (byte)'Q', (byte)'R', (byte)'S', (byte)'T', (byte)'U',
+      (byte)'V', (byte)'W', (byte)'X', (byte)'Y', (byte)'Z',
+      (byte)'_',
+      (byte)'a', (byte)'b', (byte)'c', (byte)'d', (byte)'e', (byte)'f', (byte)'g',
+      (byte)'h', (byte)'i', (byte)'j', (byte)'k', (byte)'l', (byte)'m', (byte)'n',
+      (byte)'o', (byte)'p', (byte)'q', (byte)'r', (byte)'s', (byte)'t', (byte)'u',
+      (byte)'v', (byte)'w', (byte)'x', (byte)'y', (byte)'z'
+    };
+
+	/**
+	 * Used in decoding the "ordered" dialect of Base64.
+	 */
+    private final static byte[] _ORDERED_DECODABET =
+    {
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,                 // Decimal  0 -  8
+      -5,-5,                                      // Whitespace: Tab and Linefeed
+      -9,-9,                                      // Decimal 11 - 12
+      -5,                                         // Whitespace: Carriage Return
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 14 - 26
+      -9,-9,-9,-9,-9,                             // Decimal 27 - 31
+      -5,                                         // Whitespace: Space
+      -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,              // Decimal 33 - 42
+      -9,                                         // Plus sign at decimal 43
+      -9,                                         // Decimal 44
+      0,                                          // Minus sign at decimal 45
+      -9,                                         // Decimal 46
+      -9,                                         // Slash at decimal 47
+      1,2,3,4,5,6,7,8,9,10,                       // Numbers zero through nine
+      -9,-9,-9,                                   // Decimal 58 - 60
+      -1,                                         // Equals sign at decimal 61
+      -9,-9,-9,                                   // Decimal 62 - 64
+      11,12,13,14,15,16,17,18,19,20,21,22,23,     // Letters 'A' through 'M'
+      24,25,26,27,28,29,30,31,32,33,34,35,36,     // Letters 'N' through 'Z'
+      -9,-9,-9,-9,                                // Decimal 91 - 94
+      37,                                         // Underscore at decimal 95
+      -9,                                         // Decimal 96
+      38,39,40,41,42,43,44,45,46,47,48,49,50,     // Letters 'a' through 'm'
+      51,52,53,54,55,56,57,58,59,60,61,62,63,     // Letters 'n' through 'z'
+      -9,-9,-9,-9                                 // Decimal 123 - 126
+      /*,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 127 - 139
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 140 - 152
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 153 - 165
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 166 - 178
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 179 - 191
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 192 - 204
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 205 - 217
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 218 - 230
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,     // Decimal 231 - 243
+        -9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9,-9         // Decimal 244 - 255 */
+    };
+
+
+/* ********  D E T E R M I N E   W H I C H   A L H A B E T  ******** */
+
+
+	/**
+	 * Returns one of the _SOMETHING_ALPHABET byte arrays depending on
+	 * the options specified.
+	 * It's possible, though silly, to specify ORDERED and URLSAFE
+	 * in which case one of them will be picked, though there is
+	 * no guarantee as to which one will be picked.
+	 */
+	private final static byte[] getAlphabet( int options )
+	{
+		if( (options & URL_SAFE) == URL_SAFE ) return _URL_SAFE_ALPHABET;
+		else if( (options & ORDERED) == ORDERED ) return _ORDERED_ALPHABET;
+		else return _STANDARD_ALPHABET;
+
+	}	// end getAlphabet
+
+
+	/**
+	 * Returns one of the _SOMETHING_DECODABET byte arrays depending on
+	 * the options specified.
+	 * It's possible, though silly, to specify ORDERED and URL_SAFE
+	 * in which case one of them will be picked, though there is
+	 * no guarantee as to which one will be picked.
+	 */
+	private final static byte[] getDecodabet( int options )
+	{
+		if( (options & URL_SAFE) == URL_SAFE ) return _URL_SAFE_DECODABET;
+		else if( (options & ORDERED) == ORDERED ) return _ORDERED_DECODABET;
+		else return _STANDARD_DECODABET;
+
+	}	// end getAlphabet
+
+
+
+    /** Defeats instantiation. */
+    private Base64(){}
+
+    /**
+     * Prints command line usage.
+     *
+     * @param msg A message to include with usage info.
+     */
+    private final static void usage( String msg )
+    {
+        System.err.println( msg );
+        System.err.println( "Usage: java Base64 -e|-d inputfile outputfile" );
+    }   // end usage
+
+
+/* ********  E N C O D I N G   M E T H O D S  ******** */
+
+
+    /**
+     * Encodes up to the first three bytes of array <var>threeBytes</var>
+     * and returns a four-byte array in Base64 notation.
+     * The actual number of significant bytes in your array is
+     * given by <var>numSigBytes</var>.
+     * The array <var>threeBytes</var> needs only be as big as
+     * <var>numSigBytes</var>.
+     * Code can reuse a byte array by passing a four-byte array as <var>b4</var>.
+     *
+     * @param b4 A reusable byte array to reduce array instantiation
+     * @param threeBytes the array to convert
+     * @param numSigBytes the number of significant bytes in your array
+     * @return four byte array in Base64 notation.
+     * @since 1.5.1
+     */
+    private static byte[] encode3to4( byte[] b4, byte[] threeBytes, int numSigBytes, int options )
+    {
+        encode3to4( threeBytes, 0, numSigBytes, b4, 0, options );
+        return b4;
+    }   // end encode3to4
+
+
+    /**
+     * <p>Encodes up to three bytes of the array <var>source</var>
+     * and writes the resulting four Base64 bytes to <var>destination</var>.
+     * The source and destination arrays can be manipulated
+     * anywhere along their length by specifying
+     * <var>srcOffset</var> and <var>destOffset</var>.
+     * This method does not check to make sure your arrays
+     * are large enough to accomodate <var>srcOffset</var> + 3 for
+     * the <var>source</var> array or <var>destOffset</var> + 4 for
+     * the <var>destination</var> array.
+     * The actual number of significant bytes in your array is
+     * given by <var>numSigBytes</var>.</p>
+	 * <p>This is the lowest level of the encoding methods with
+	 * all possible parameters.</p>
+     *
+     * @param source the array to convert
+     * @param srcOffset the index where conversion begins
+     * @param numSigBytes the number of significant bytes in your array
+     * @param destination the array to hold the conversion
+     * @param destOffset the index where output will be put
+     * @return the <var>destination</var> array
+     * @since 1.3
+     */
+    private static byte[] encode3to4(
+     byte[] source, int srcOffset, int numSigBytes,
+     byte[] destination, int destOffset, int options )
+    {
+		byte[] ALPHABET = getAlphabet( options );
+
+        //           1         2         3
+        // 01234567890123456789012345678901 Bit position
+        // --------000000001111111122222222 Array position from threeBytes
+        // --------|    ||    ||    ||    | Six bit groups to index ALPHABET
+        //          >>18  >>12  >> 6  >> 0  Right shift necessary
+        //                0x3f  0x3f  0x3f  Additional AND
+
+        // Create buffer with zero-padding if there are only one or two
+        // significant bytes passed in the array.
+        // We have to shift left 24 in order to flush out the 1's that appear
+        // when Java treats a value as negative that is cast from a byte to an int.
+        int inBuff =   ( numSigBytes > 0 ? ((source[ srcOffset     ] << 24) >>>  8) : 0 )
+                     | ( numSigBytes > 1 ? ((source[ srcOffset + 1 ] << 24) >>> 16) : 0 )
+                     | ( numSigBytes > 2 ? ((source[ srcOffset + 2 ] << 24) >>> 24) : 0 );
+
+        switch( numSigBytes )
+        {
+            case 3:
+                destination[ destOffset     ] = ALPHABET[ (inBuff >>> 18)        ];
+                destination[ destOffset + 1 ] = ALPHABET[ (inBuff >>> 12) & 0x3f ];
+                destination[ destOffset + 2 ] = ALPHABET[ (inBuff >>>  6) & 0x3f ];
+                destination[ destOffset + 3 ] = ALPHABET[ (inBuff       ) & 0x3f ];
+                return destination;
+
+            case 2:
+                destination[ destOffset     ] = ALPHABET[ (inBuff >>> 18)        ];
+                destination[ destOffset + 1 ] = ALPHABET[ (inBuff >>> 12) & 0x3f ];
+                destination[ destOffset + 2 ] = ALPHABET[ (inBuff >>>  6) & 0x3f ];
+                destination[ destOffset + 3 ] = EQUALS_SIGN;
+                return destination;
+
+            case 1:
+                destination[ destOffset     ] = ALPHABET[ (inBuff >>> 18)        ];
+                destination[ destOffset + 1 ] = ALPHABET[ (inBuff >>> 12) & 0x3f ];
+                destination[ destOffset + 2 ] = EQUALS_SIGN;
+                destination[ destOffset + 3 ] = EQUALS_SIGN;
+                return destination;
+
+            default:
+                return destination;
+        }   // end switch
+    }   // end encode3to4
+
+
+
+    /**
+     * Serializes an object and returns the Base64-encoded
+     * version of that serialized object. If the object
+     * cannot be serialized or there is another error,
+     * the method will return <tt>null</tt>.
+     * The object is not GZip-compressed before being encoded.
+     *
+     * @param serializableObject The object to encode
+     * @return The Base64-encoded object
+     * @since 1.4
+     */
+    public static String encodeObject( java.io.Serializable serializableObject )
+    {
+        return encodeObject( serializableObject, NO_OPTIONS );
+    }   // end encodeObject
+
+
+
+    /**
+     * Serializes an object and returns the Base64-encoded
+     * version of that serialized object. If the object
+     * cannot be serialized or there is another error,
+     * the method will return <tt>null</tt>.
+     * <p>
+     * Valid options:<pre>
+     *   GZIP: gzip-compresses object before encoding it.
+     *   DONT_BREAK_LINES: don't break lines at 76 characters
+     *     <i>Note: Technically, this makes your encoding non-compliant.</i>
+     * </pre>
+     * <p>
+     * Example: <code>encodeObject( myObj, Base64.GZIP )</code> or
+     * <p>
+     * Example: <code>encodeObject( myObj, Base64.GZIP | Base64.DONT_BREAK_LINES )</code>
+     *
+     * @param serializableObject The object to encode
+     * @param options Specified options
+     * @return The Base64-encoded object
+     * @see Base64#GZIP
+     * @see Base64#DONT_BREAK_LINES
+     * @since 2.0
+     */
+    public static String encodeObject( java.io.Serializable serializableObject, int options )
+    {
+        // Streams
+        java.io.ByteArrayOutputStream  baos  = null;
+        java.io.OutputStream           b64os = null;
+        java.io.ObjectOutputStream     oos   = null;
+        java.util.zip.GZIPOutputStream gzos  = null;
+
+        // Isolate options
+        int gzip           = (options & GZIP);
+        int dontBreakLines = (options & DONT_BREAK_LINES);
+
+        try
+        {
+            // ObjectOutputStream -> (GZIP) -> Base64 -> ByteArrayOutputStream
+            baos  = new java.io.ByteArrayOutputStream();
+            b64os = new Base64.OutputStream( baos, ENCODE | options );
+
+            // GZip?
+            if( gzip == GZIP )
+            {
+                gzos = new java.util.zip.GZIPOutputStream( b64os );
+                oos  = new java.io.ObjectOutputStream( gzos );
+            }   // end if: gzip
+            else
+                oos   = new java.io.ObjectOutputStream( b64os );
+
+            oos.writeObject( serializableObject );
+        }   // end try
+        catch( java.io.IOException e )
+        {
+            e.printStackTrace();
+            return null;
+        }   // end catch
+        finally
+        {
+            try{ oos.close();   } catch( Exception e ){}
+            try{ gzos.close();  } catch( Exception e ){}
+            try{ b64os.close(); } catch( Exception e ){}
+            try{ baos.close();  } catch( Exception e ){}
+        }   // end finally
+
+        // Return value according to relevant encoding.
+        try
+        {
+            return new String( baos.toByteArray(), PREFERRED_ENCODING );
+        }   // end try
+        catch (java.io.UnsupportedEncodingException uue)
+        {
+            return new String( baos.toByteArray() );
+        }   // end catch
+
+    }   // end encode
+
+
+
+    /**
+     * Encodes a byte array into Base64 notation.
+     * Does not GZip-compress data.
+     *
+     * @param source The data to convert
+     * @since 1.4
+     */
+    public static String encodeBytes( byte[] source )
+    {
+        return encodeBytes( source, 0, source.length, NO_OPTIONS );
+    }   // end encodeBytes
+
+
+
+    /**
+     * Encodes a byte array into Base64 notation.
+     * <p>
+     * Valid options:<pre>
+     *   GZIP: gzip-compresses object before encoding it.
+     *   DONT_BREAK_LINES: don't break lines at 76 characters
+     *     <i>Note: Technically, this makes your encoding non-compliant.</i>
+     * </pre>
+     * <p>
+     * Example: <code>encodeBytes( myData, Base64.GZIP )</code> or
+     * <p>
+     * Example: <code>encodeBytes( myData, Base64.GZIP | Base64.DONT_BREAK_LINES )</code>
+     *
+     *
+     * @param source The data to convert
+     * @param options Specified options
+     * @see Base64#GZIP
+     * @see Base64#DONT_BREAK_LINES
+     * @since 2.0
+     */
+    public static String encodeBytes( byte[] source, int options )
+    {
+        return encodeBytes( source, 0, source.length, options );
+    }   // end encodeBytes
+
+
+    /**
+     * Encodes a byte array into Base64 notation.
+     * Does not GZip-compress data.
+     *
+     * @param source The data to convert
+     * @param off Offset in array where conversion should begin
+     * @param len Length of data to convert
+     * @since 1.4
+     */
+    public static String encodeBytes( byte[] source, int off, int len )
+    {
+        return encodeBytes( source, off, len, NO_OPTIONS );
+    }   // end encodeBytes
+
+
+
+    /**
+     * Encodes a byte array into Base64 notation.
+     * <p>
+     * Valid options:<pre>
+     *   GZIP: gzip-compresses object before encoding it.
+     *   DONT_BREAK_LINES: don't break lines at 76 characters
+     *     <i>Note: Technically, this makes your encoding non-compliant.</i>
+     * </pre>
+     * <p>
+     * Example: <code>encodeBytes( myData, Base64.GZIP )</code> or
+     * <p>
+     * Example: <code>encodeBytes( myData, Base64.GZIP | Base64.DONT_BREAK_LINES )</code>
+     *
+     *
+     * @param source The data to convert
+     * @param off Offset in array where conversion should begin
+     * @param len Length of data to convert
+     * @param options Specified options; alphabet type is pulled from this (standard, url-safe, ordered)
+     * @see Base64#GZIP
+     * @see Base64#DONT_BREAK_LINES
+     * @since 2.0
+     */
+    public static String encodeBytes( byte[] source, int off, int len, int options )
+    {
+        // Isolate options
+        int dontBreakLines = ( options & DONT_BREAK_LINES );
+        int gzip           = ( options & GZIP   );
+
+        // Compress?
+        if( gzip == GZIP )
+        {
+            java.io.ByteArrayOutputStream  baos  = null;
+            java.util.zip.GZIPOutputStream gzos  = null;
+            Base64.OutputStream            b64os = null;
+
+
+            try
+            {
+                // GZip -> Base64 -> ByteArray
+                baos = new java.io.ByteArrayOutputStream();
+                b64os = new Base64.OutputStream( baos, ENCODE | options );
+                gzos  = new java.util.zip.GZIPOutputStream( b64os );
+
+                gzos.write( source, off, len );
+                gzos.close();
+            }   // end try
+            catch( java.io.IOException e )
+            {
+                e.printStackTrace();
+                return null;
+            }   // end catch
+            finally
+            {
+                try{ gzos.close();  } catch( Exception e ){}
+                try{ b64os.close(); } catch( Exception e ){}
+                try{ baos.close();  } catch( Exception e ){}
+            }   // end finally
+
+            // Return value according to relevant encoding.
+            try
+            {
+                return new String( baos.toByteArray(), PREFERRED_ENCODING );
+            }   // end try
+            catch (java.io.UnsupportedEncodingException uue)
+            {
+                return new String( baos.toByteArray() );
+            }   // end catch
+        }   // end if: compress
+
+        // Else, don't compress. Better not to use streams at all then.
+        else
+        {
+            // Convert option to boolean in way that code likes it.
+            boolean breakLines = dontBreakLines == 0;
+
+            int    len43   = len * 4 / 3;
+            byte[] outBuff = new byte[   ( len43 )                      // Main 4:3
+                                       + ( (len % 3) > 0 ? 4 : 0 )      // Account for padding
+                                       + (breakLines ? ( len43 / MAX_LINE_LENGTH ) : 0) ]; // New lines
+            int d = 0;
+            int e = 0;
+            int len2 = len - 2;
+            int lineLength = 0;
+            for( ; d < len2; d+=3, e+=4 )
+            {
+                encode3to4( source, d+off, 3, outBuff, e, options );
+
+                lineLength += 4;
+                if( breakLines && lineLength == MAX_LINE_LENGTH )
+                {
+                    outBuff[e+4] = NEW_LINE;
+                    e++;
+                    lineLength = 0;
+                }   // end if: end of line
+            }   // en dfor: each piece of array
+
+            if( d < len )
+            {
+                encode3to4( source, d+off, len - d, outBuff, e, options );
+                e += 4;
+            }   // end if: some padding needed
+
+
+            // Return value according to relevant encoding.
+            try
+            {
+                return new String( outBuff, 0, e, PREFERRED_ENCODING );
+            }   // end try
+            catch (java.io.UnsupportedEncodingException uue)
+            {
+                return new String( outBuff, 0, e );
+            }   // end catch
+
+        }   // end else: don't compress
+
+    }   // end encodeBytes
+
+
+
+
+
+/* ********  D E C O D I N G   M E T H O D S  ******** */
+
+
+    /**
+     * Decodes four bytes from array <var>source</var>
+     * and writes the resulting bytes (up to three of them)
+     * to <var>destination</var>.
+     * The source and destination arrays can be manipulated
+     * anywhere along their length by specifying
+     * <var>srcOffset</var> and <var>destOffset</var>.
+     * This method does not check to make sure your arrays
+     * are large enough to accomodate <var>srcOffset</var> + 4 for
+     * the <var>source</var> array or <var>destOffset</var> + 3 for
+     * the <var>destination</var> array.
+     * This method returns the actual number of bytes that
+     * were converted from the Base64 encoding.
+	 * <p>This is the lowest level of the decoding methods with
+	 * all possible parameters.</p>
+     *
+     *
+     * @param source the array to convert
+     * @param srcOffset the index where conversion begins
+     * @param destination the array to hold the conversion
+     * @param destOffset the index where output will be put
+	 * @param options alphabet type is pulled from this (standard, url-safe, ordered)
+     * @return the number of decoded bytes converted
+     * @since 1.3
+     */
+    private static int decode4to3( byte[] source, int srcOffset, byte[] destination, int destOffset, int options )
+    {
+		byte[] DECODABET = getDecodabet( options );
+
+        // Example: Dk==
+        if( source[ srcOffset + 2] == EQUALS_SIGN )
+        {
+            // Two ways to do the same thing. Don't know which way I like best.
+            //int outBuff =   ( ( DECODABET[ source[ srcOffset    ] ] << 24 ) >>>  6 )
+            //              | ( ( DECODABET[ source[ srcOffset + 1] ] << 24 ) >>> 12 );
+            int outBuff =   ( ( DECODABET[ source[ srcOffset    ] ] & 0xFF ) << 18 )
+                          | ( ( DECODABET[ source[ srcOffset + 1] ] & 0xFF ) << 12 );
+
+            destination[ destOffset ] = (byte)( outBuff >>> 16 );
+            return 1;
+        }
+
+        // Example: DkL=
+        else if( source[ srcOffset + 3 ] == EQUALS_SIGN )
+        {
+            // Two ways to do the same thing. Don't know which way I like best.
+            //int outBuff =   ( ( DECODABET[ source[ srcOffset     ] ] << 24 ) >>>  6 )
+            //              | ( ( DECODABET[ source[ srcOffset + 1 ] ] << 24 ) >>> 12 )
+            //              | ( ( DECODABET[ source[ srcOffset + 2 ] ] << 24 ) >>> 18 );
+            int outBuff =   ( ( DECODABET[ source[ srcOffset     ] ] & 0xFF ) << 18 )
+                          | ( ( DECODABET[ source[ srcOffset + 1 ] ] & 0xFF ) << 12 )
+                          | ( ( DECODABET[ source[ srcOffset + 2 ] ] & 0xFF ) <<  6 );
+
+            destination[ destOffset     ] = (byte)( outBuff >>> 16 );
+            destination[ destOffset + 1 ] = (byte)( outBuff >>>  8 );
+            return 2;
+        }
+
+        // Example: DkLE
+        else
+        {
+            try{
+            // Two ways to do the same thing. Don't know which way I like best.
+            //int outBuff =   ( ( DECODABET[ source[ srcOffset     ] ] << 24 ) >>>  6 )
+            //              | ( ( DECODABET[ source[ srcOffset + 1 ] ] << 24 ) >>> 12 )
+            //              | ( ( DECODABET[ source[ srcOffset + 2 ] ] << 24 ) >>> 18 )
+            //              | ( ( DECODABET[ source[ srcOffset + 3 ] ] << 24 ) >>> 24 );
+            int outBuff =   ( ( DECODABET[ source[ srcOffset     ] ] & 0xFF ) << 18 )
+                          | ( ( DECODABET[ source[ srcOffset + 1 ] ] & 0xFF ) << 12 )
+                          | ( ( DECODABET[ source[ srcOffset + 2 ] ] & 0xFF ) <<  6)
+                          | ( ( DECODABET[ source[ srcOffset + 3 ] ] & 0xFF )      );
+
+
+            destination[ destOffset     ] = (byte)( outBuff >> 16 );
+            destination[ destOffset + 1 ] = (byte)( outBuff >>  8 );
+            destination[ destOffset + 2 ] = (byte)( outBuff       );
+
+            return 3;
+            }catch( Exception e){
+                System.out.println(""+source[srcOffset]+ ": " + ( DECODABET[ source[ srcOffset     ] ]  ) );
+                System.out.println(""+source[srcOffset+1]+  ": " + ( DECODABET[ source[ srcOffset + 1 ] ]  ) );
+                System.out.println(""+source[srcOffset+2]+  ": " + ( DECODABET[ source[ srcOffset + 2 ] ]  ) );
+                System.out.println(""+source[srcOffset+3]+  ": " + ( DECODABET[ source[ srcOffset + 3 ] ]  ) );
+                return -1;
+            }   // end catch
+        }
+    }   // end decodeToBytes
+
+
+
+
+    /**
+     * Very low-level access to decoding ASCII characters in
+     * the form of a byte array. Does not support automatically
+     * gunzipping or any other "fancy" features.
+     *
+     * @param source The Base64 encoded data
+     * @param off    The offset of where to begin decoding
+     * @param len    The length of characters to decode
+     * @return decoded data
+     * @since 1.3
+     */
+    public static byte[] decode( byte[] source, int off, int len, int options )
+    {
+		byte[] DECODABET = getDecodabet( options );
+
+        int    len34   = len * 3 / 4;
+        byte[] outBuff = new byte[ len34 ]; // Upper limit on size of output
+        int    outBuffPosn = 0;
+
+        byte[] b4        = new byte[4];
+        int    b4Posn    = 0;
+        int    i         = 0;
+        byte   sbiCrop   = 0;
+        byte   sbiDecode = 0;
+        for( i = off; i < off+len; i++ )
+        {
+            sbiCrop = (byte)(source[i] & 0x7f); // Only the low seven bits
+            sbiDecode = DECODABET[ sbiCrop ];
+
+            if( sbiDecode >= WHITE_SPACE_ENC ) // White space, Equals sign or better
+            {
+                if( sbiDecode >= EQUALS_SIGN_ENC )
+                {
+                    b4[ b4Posn++ ] = sbiCrop;
+                    if( b4Posn > 3 )
+                    {
+                        outBuffPosn += decode4to3( b4, 0, outBuff, outBuffPosn, options );
+                        b4Posn = 0;
+
+                        // If that was the equals sign, break out of 'for' loop
+                        if( sbiCrop == EQUALS_SIGN )
+                            break;
+                    }   // end if: quartet built
+
+                }   // end if: equals sign or better
+
+            }   // end if: white space, equals sign or better
+            else
+            {
+                System.err.println( "Bad Base64 input character at " + i + ": " + source[i] + "(decimal)" );
+                return null;
+            }   // end else:
+        }   // each input character
+
+        byte[] out = new byte[ outBuffPosn ];
+        System.arraycopy( outBuff, 0, out, 0, outBuffPosn );
+        return out;
+    }   // end decode
+
+
+
+
+    /**
+     * Decodes data from Base64 notation, automatically
+     * detecting gzip-compressed data and decompressing it.
+     *
+     * @param s the string to decode
+     * @return the decoded data
+     * @since 1.4
+     */
+    public static byte[] decode( String s )
+	{
+		return decode( s, NO_OPTIONS );
+	}
+
+
+    /**
+     * Decodes data from Base64 notation, automatically
+     * detecting gzip-compressed data and decompressing it.
+     *
+     * @param s the string to decode
+	 * @param options encode options such as URL_SAFE
+     * @return the decoded data
+     * @since 1.4
+     */
+    public static byte[] decode( String s, int options )
+    {
+        byte[] bytes;
+        try
+        {
+            bytes = s.getBytes( PREFERRED_ENCODING );
+        }   // end try
+        catch( java.io.UnsupportedEncodingException uee )
+        {
+            bytes = s.getBytes();
+        }   // end catch
+		//</change>
+
+        // Decode
+        bytes = decode( bytes, 0, bytes.length, options );
+
+
+        // Check to see if it's gzip-compressed
+        // GZIP Magic Two-Byte Number: 0x8b1f (35615)
+        if( bytes != null && bytes.length >= 4 )
+        {
+
+            int head = ((int)bytes[0] & 0xff) | ((bytes[1] << 8) & 0xff00);
+            if( java.util.zip.GZIPInputStream.GZIP_MAGIC == head )
+            {
+                java.io.ByteArrayInputStream  bais = null;
+                java.util.zip.GZIPInputStream gzis = null;
+                java.io.ByteArrayOutputStream baos = null;
+                byte[] buffer = new byte[2048];
+                int    length = 0;
+
+                try
+                {
+                    baos = new java.io.ByteArrayOutputStream();
+                    bais = new java.io.ByteArrayInputStream( bytes );
+                    gzis = new java.util.zip.GZIPInputStream( bais );
+
+                    while( ( length = gzis.read( buffer ) ) >= 0 )
+                    {
+                        baos.write(buffer,0,length);
+                    }   // end while: reading input
+
+                    // No error? Get new bytes.
+                    bytes = baos.toByteArray();
+
+                }   // end try
+                catch( java.io.IOException e )
+                {
+                    // Just return originally-decoded bytes
+                }   // end catch
+                finally
+                {
+                    try{ baos.close(); } catch( Exception e ){}
+                    try{ gzis.close(); } catch( Exception e ){}
+                    try{ bais.close(); } catch( Exception e ){}
+                }   // end finally
+
+            }   // end if: gzipped
+        }   // end if: bytes.length >= 2
+
+        return bytes;
+    }   // end decode
+
+
+
+
+    /**
+     * Attempts to decode Base64 data and deserialize a Java
+     * Object within. Returns <tt>null</tt> if there was an error.
+     *
+     * @param encodedObject The Base64 data to decode
+     * @return The decoded and deserialized object
+     * @since 1.5
+     */
+    public static Object decodeToObject( String encodedObject )
+    {
+        // Decode and gunzip if necessary
+        byte[] objBytes = decode( encodedObject );
+
+        java.io.ByteArrayInputStream  bais = null;
+        java.io.ObjectInputStream     ois  = null;
+        Object obj = null;
+
+        try
+        {
+            bais = new java.io.ByteArrayInputStream( objBytes );
+            ois  = new java.io.ObjectInputStream( bais );
+
+            obj = ois.readObject();
+        }   // end try
+        catch( java.io.IOException e )
+        {
+            e.printStackTrace();
+            obj = null;
+        }   // end catch
+        catch( java.lang.ClassNotFoundException e )
+        {
+            e.printStackTrace();
+            obj = null;
+        }   // end catch
+        finally
+        {
+            try{ bais.close(); } catch( Exception e ){}
+            try{ ois.close();  } catch( Exception e ){}
+        }   // end finally
+
+        return obj;
+    }   // end decodeObject
+
+
+
+    /**
+     * Convenience method for encoding data to a file.
+     *
+     * @param dataToEncode byte array of data to encode in base64 form
+     * @param filename Filename for saving encoded data
+     * @return <tt>true</tt> if successful, <tt>false</tt> otherwise
+     *
+     * @since 2.1
+     */
+    public static boolean encodeToFile( byte[] dataToEncode, String filename )
+    {
+        boolean success = false;
+        Base64.OutputStream bos = null;
+        try
+        {
+            bos = new Base64.OutputStream(
+                      new java.io.FileOutputStream( filename ), Base64.ENCODE );
+            bos.write( dataToEncode );
+            success = true;
+        }   // end try
+        catch( java.io.IOException e )
+        {
+
+            success = false;
+        }   // end catch: IOException
+        finally
+        {
+            try{ bos.close(); } catch( Exception e ){}
+        }   // end finally
+
+        return success;
+    }   // end encodeToFile
+
+
+    /**
+     * Convenience method for decoding data to a file.
+     *
+     * @param dataToDecode Base64-encoded data as a string
+     * @param filename Filename for saving decoded data
+     * @return <tt>true</tt> if successful, <tt>false</tt> otherwise
+     *
+     * @since 2.1
+     */
+    public static boolean decodeToFile( String dataToDecode, String filename )
+    {
+        boolean success = false;
+        Base64.OutputStream bos = null;
+        try
+        {
+                bos = new Base64.OutputStream(
+                          new java.io.FileOutputStream( filename ), Base64.DECODE );
+                bos.write( dataToDecode.getBytes( PREFERRED_ENCODING ) );
+                success = true;
+        }   // end try
+        catch( java.io.IOException e )
+        {
+            success = false;
+        }   // end catch: IOException
+        finally
+        {
+                try{ bos.close(); } catch( Exception e ){}
+        }   // end finally
+
+        return success;
+    }   // end decodeToFile
+
+
+
+
+    /**
+     * Convenience method for reading a base64-encoded
+     * file and decoding it.
+     *
+     * @param filename Filename for reading encoded data
+     * @return decoded byte array or null if unsuccessful
+     *
+     * @since 2.1
+     */
+    public static byte[] decodeFromFile( String filename )
+    {
+        byte[] decodedData = null;
+        Base64.InputStream bis = null;
+        try
+        {
+            // Set up some useful variables
+            java.io.File file = new java.io.File( filename );
+            byte[] buffer = null;
+            int length   = 0;
+            int numBytes = 0;
+
+            // Check for size of file
+            if( file.length() > Integer.MAX_VALUE )
+            {
+                System.err.println( "File is too big for this convenience method (" + file.length() + " bytes)." );
+                return null;
+            }   // end if: file too big for int index
+            buffer = new byte[ (int)file.length() ];
+
+            // Open a stream
+            bis = new Base64.InputStream(
+                      new java.io.BufferedInputStream(
+                      new java.io.FileInputStream( file ) ), Base64.DECODE );
+
+            // Read until done
+            while( ( numBytes = bis.read( buffer, length, 4096 ) ) >= 0 )
+                length += numBytes;
+
+            // Save in a variable to return
+            decodedData = new byte[ length ];
+            System.arraycopy( buffer, 0, decodedData, 0, length );
+
+        }   // end try
+        catch( java.io.IOException e )
+        {
+            System.err.println( "Error decoding from file " + filename );
+        }   // end catch: IOException
+        finally
+        {
+            try{ bis.close(); } catch( Exception e) {}
+        }   // end finally
+
+        return decodedData;
+    }   // end decodeFromFile
+
+
+
+    /**
+     * Convenience method for reading a binary file
+     * and base64-encoding it.
+     *
+     * @param filename Filename for reading binary data
+     * @return base64-encoded string or null if unsuccessful
+     *
+     * @since 2.1
+     */
+    public static String encodeFromFile( String filename )
+    {
+        String encodedData = null;
+        Base64.InputStream bis = null;
+        try
+        {
+            // Set up some useful variables
+            java.io.File file = new java.io.File( filename );
+            byte[] buffer = new byte[ Math.max((int)(file.length() * 1.4),40) ]; // Need max() for math on small files (v2.2.1)
+            int length   = 0;
+            int numBytes = 0;
+
+            // Open a stream
+            bis = new Base64.InputStream(
+                      new java.io.BufferedInputStream(
+                      new java.io.FileInputStream( file ) ), Base64.ENCODE );
+
+            // Read until done
+            while( ( numBytes = bis.read( buffer, length, 4096 ) ) >= 0 )
+                length += numBytes;
+
+            // Save in a variable to return
+            encodedData = new String( buffer, 0, length, Base64.PREFERRED_ENCODING );
+
+        }   // end try
+        catch( java.io.IOException e )
+        {
+            System.err.println( "Error encoding from file " + filename );
+        }   // end catch: IOException
+        finally
+        {
+            try{ bis.close(); } catch( Exception e) {}
+        }   // end finally
+
+        return encodedData;
+        }   // end encodeFromFile
+
+    /**
+     * Reads <tt>infile</tt> and encodes it to <tt>outfile</tt>.
+     *
+     * @param infile Input file
+     * @param outfile Output file
+     * @since 2.2
+     */
+    public static void encodeFileToFile( String infile, String outfile )
+    {
+        String encoded = Base64.encodeFromFile( infile );
+        java.io.OutputStream out = null;
+        try{
+            out = new java.io.BufferedOutputStream(
+                  new java.io.FileOutputStream( outfile ) );
+            out.write( encoded.getBytes("US-ASCII") ); // Strict, 7-bit output.
+        }   // end try
+        catch( java.io.IOException ex ) {
+            ex.printStackTrace();
+        }   // end catch
+        finally {
+            try { out.close(); }
+            catch( Exception ex ){}
+        }   // end finally
+    }   // end encodeFileToFile
+
+
+    /**
+     * Reads <tt>infile</tt> and decodes it to <tt>outfile</tt>.
+     *
+     * @param infile Input file
+     * @param outfile Output file
+     * @since 2.2
+     */
+    public static void decodeFileToFile( String infile, String outfile )
+    {
+        byte[] decoded = Base64.decodeFromFile( infile );
+        java.io.OutputStream out = null;
+        try{
+            out = new java.io.BufferedOutputStream(
+                  new java.io.FileOutputStream( outfile ) );
+            out.write( decoded );
+        }   // end try
+        catch( java.io.IOException ex ) {
+            ex.printStackTrace();
+        }   // end catch
+        finally {
+            try { out.close(); }
+            catch( Exception ex ){}
+        }   // end finally
+    }   // end decodeFileToFile
+
+
+    /* ********  I N N E R   C L A S S   I N P U T S T R E A M  ******** */
+
+
+
+    /**
+     * A {@link Base64.InputStream} will read data from another
+     * <tt>java.io.InputStream</tt>, given in the constructor,
+     * and encode/decode to/from Base64 notation on the fly.
+     *
+     * @see Base64
+     * @since 1.3
+     */
+    public static class InputStream extends java.io.FilterInputStream
+    {
+        private boolean encode;         // Encoding or decoding
+        private int     position;       // Current position in the buffer
+        private byte[]  buffer;         // Small buffer holding converted data
+        private int     bufferLength;   // Length of buffer (3 or 4)
+        private int     numSigBytes;    // Number of meaningful bytes in the buffer
+        private int     lineLength;
+        private boolean breakLines;     // Break lines at less than 80 characters
+		private int     options;        // Record options used to create the stream.
+		private byte[]  alphabet;	    // Local copies to avoid extra method calls
+		private byte[]  decodabet;		// Local copies to avoid extra method calls
+
+
+        /**
+         * Constructs a {@link Base64.InputStream} in DECODE mode.
+         *
+         * @param in the <tt>java.io.InputStream</tt> from which to read data.
+         * @since 1.3
+         */
+        public InputStream( java.io.InputStream in )
+        {
+            this( in, DECODE );
+        }   // end constructor
+
+
+        /**
+         * Constructs a {@link Base64.InputStream} in
+         * either ENCODE or DECODE mode.
+         * <p>
+         * Valid options:<pre>
+         *   ENCODE or DECODE: Encode or Decode as data is read.
+         *   DONT_BREAK_LINES: don't break lines at 76 characters
+         *     (only meaningful when encoding)
+         *     <i>Note: Technically, this makes your encoding non-compliant.</i>
+         * </pre>
+         * <p>
+         * Example: <code>new Base64.InputStream( in, Base64.DECODE )</code>
+         *
+         *
+         * @param in the <tt>java.io.InputStream</tt> from which to read data.
+         * @param options Specified options
+         * @see Base64#ENCODE
+         * @see Base64#DECODE
+         * @see Base64#DONT_BREAK_LINES
+         * @since 2.0
+         */
+        public InputStream( java.io.InputStream in, int options )
+        {
+            super( in );
+            this.breakLines   = (options & DONT_BREAK_LINES) != DONT_BREAK_LINES;
+            this.encode       = (options & ENCODE) == ENCODE;
+            this.bufferLength = encode ? 4 : 3;
+            this.buffer       = new byte[ bufferLength ];
+            this.position     = -1;
+            this.lineLength   = 0;
+			this.options      = options; // Record for later, mostly to determine which alphabet to use
+			this.alphabet     = getAlphabet(options);
+			this.decodabet    = getDecodabet(options);
+        }   // end constructor
+
+        /**
+         * Reads enough of the input stream to convert
+         * to/from Base64 and returns the next byte.
+         *
+         * @return next byte
+         * @since 1.3
+         */
+        public int read() throws java.io.IOException
+        {
+            // Do we need to get data?
+            if( position < 0 )
+            {
+                if( encode )
+                {
+                    byte[] b3 = new byte[3];
+                    int numBinaryBytes = 0;
+                    for( int i = 0; i < 3; i++ )
+                    {
+                        try
+                        {
+                            int b = in.read();
+
+                            // If end of stream, b is -1.
+                            if( b >= 0 )
+                            {
+                                b3[i] = (byte)b;
+                                numBinaryBytes++;
+                            }   // end if: not end of stream
+
+                        }   // end try: read
+                        catch( java.io.IOException e )
+                        {
+                            // Only a problem if we got no data at all.
+                            if( i == 0 )
+                                throw e;
+
+                        }   // end catch
+                    }   // end for: each needed input byte
+
+                    if( numBinaryBytes > 0 )
+                    {
+                        encode3to4( b3, 0, numBinaryBytes, buffer, 0, options );
+                        position = 0;
+                        numSigBytes = 4;
+                    }   // end if: got data
+                    else
+                    {
+                        return -1;
+                    }   // end else
+                }   // end if: encoding
+
+                // Else decoding
+                else
+                {
+                    byte[] b4 = new byte[4];
+                    int i = 0;
+                    for( i = 0; i < 4; i++ )
+                    {
+                        // Read four "meaningful" bytes:
+                        int b = 0;
+                        do{ b = in.read(); }
+                        while( b >= 0 && decodabet[ b & 0x7f ] <= WHITE_SPACE_ENC );
+
+                        if( b < 0 )
+                            break; // Reads a -1 if end of stream
+
+                        b4[i] = (byte)b;
+                    }   // end for: each needed input byte
+
+                    if( i == 4 )
+                    {
+                        numSigBytes = decode4to3( b4, 0, buffer, 0, options );
+                        position = 0;
+                    }   // end if: got four characters
+                    else if( i == 0 ){
+                        return -1;
+                    }   // end else if: also padded correctly
+                    else
+                    {
+                        // Must have broken out from above.
+                        throw new java.io.IOException( "Improperly padded Base64 input." );
+                    }   // end
+
+                }   // end else: decode
+            }   // end else: get data
+
+            // Got data?
+            if( position >= 0 )
+            {
+                // End of relevant data?
+                if( /*!encode &&*/ position >= numSigBytes )
+                    return -1;
+
+                if( encode && breakLines && lineLength >= MAX_LINE_LENGTH )
+                {
+                    lineLength = 0;
+                    return '\n';
+                }   // end if
+                else
+                {
+                    lineLength++;   // This isn't important when decoding
+                                    // but throwing an extra "if" seems
+                                    // just as wasteful.
+
+                    int b = buffer[ position++ ];
+
+                    if( position >= bufferLength )
+                        position = -1;
+
+                    return b & 0xFF; // This is how you "cast" a byte that's
+                                     // intended to be unsigned.
+                }   // end else
+            }   // end if: position >= 0
+
+            // Else error
+            else
+            {
+                // When JDK1.4 is more accepted, use an assertion here.
+                throw new java.io.IOException( "Error in Base64 code reading stream." );
+            }   // end else
+        }   // end read
+
+
+        /**
+         * Calls {@link #read()} repeatedly until the end of stream
+         * is reached or <var>len</var> bytes are read.
+         * Returns number of bytes read into array or -1 if
+         * end of stream is encountered.
+         *
+         * @param dest array to hold values
+         * @param off offset for array
+         * @param len max number of bytes to read into array
+         * @return bytes read into array or -1 if end of stream is encountered.
+         * @since 1.3
+         */
+        public int read( byte[] dest, int off, int len ) throws java.io.IOException
+        {
+            int i;
+            int b;
+            for( i = 0; i < len; i++ )
+            {
+                b = read();
+
+                //if( b < 0 && i == 0 )
+                //    return -1;
+
+                if( b >= 0 )
+                    dest[off + i] = (byte)b;
+                else if( i == 0 )
+                    return -1;
+                else
+                    break; // Out of 'for' loop
+            }   // end for: each byte read
+            return i;
+        }   // end read
+
+    }   // end inner class InputStream
+
+
+
+
+
+
+    /* ********  I N N E R   C L A S S   O U T P U T S T R E A M  ******** */
+
+
+
+    /**
+     * A {@link Base64.OutputStream} will write data to another
+     * <tt>java.io.OutputStream</tt>, given in the constructor,
+     * and encode/decode to/from Base64 notation on the fly.
+     *
+     * @see Base64
+     * @since 1.3
+     */
+    public static class OutputStream extends java.io.FilterOutputStream
+    {
+        private boolean encode;
+        private int     position;
+        private byte[]  buffer;
+        private int     bufferLength;
+        private int     lineLength;
+        private boolean breakLines;
+        private byte[]  b4; // Scratch used in a few places
+        private boolean suspendEncoding;
+		private int options; // Record for later
+		private byte[]  alphabet;	    // Local copies to avoid extra method calls
+		private byte[]  decodabet;		// Local copies to avoid extra method calls
+
+        /**
+         * Constructs a {@link Base64.OutputStream} in ENCODE mode.
+         *
+         * @param out the <tt>java.io.OutputStream</tt> to which data will be written.
+         * @since 1.3
+         */
+        public OutputStream( java.io.OutputStream out )
+        {
+            this( out, ENCODE );
+        }   // end constructor
+
+
+        /**
+         * Constructs a {@link Base64.OutputStream} in
+         * either ENCODE or DECODE mode.
+         * <p>
+         * Valid options:<pre>
+         *   ENCODE or DECODE: Encode or Decode as data is read.
+         *   DONT_BREAK_LINES: don't break lines at 76 characters
+         *     (only meaningful when encoding)
+         *     <i>Note: Technically, this makes your encoding non-compliant.</i>
+         * </pre>
+         * <p>
+         * Example: <code>new Base64.OutputStream( out, Base64.ENCODE )</code>
+         *
+         * @param out the <tt>java.io.OutputStream</tt> to which data will be written.
+         * @param options Specified options.
+         * @see Base64#ENCODE
+         * @see Base64#DECODE
+         * @see Base64#DONT_BREAK_LINES
+         * @since 1.3
+         */
+        public OutputStream( java.io.OutputStream out, int options )
+        {
+            super( out );
+            this.breakLines   = (options & DONT_BREAK_LINES) != DONT_BREAK_LINES;
+            this.encode       = (options & ENCODE) == ENCODE;
+            this.bufferLength = encode ? 3 : 4;
+            this.buffer       = new byte[ bufferLength ];
+            this.position     = 0;
+            this.lineLength   = 0;
+            this.suspendEncoding = false;
+            this.b4           = new byte[4];
+			this.options      = options;
+			this.alphabet     = getAlphabet(options);
+			this.decodabet    = getDecodabet(options);
+        }   // end constructor
+
+
+        /**
+         * Writes the byte to the output stream after
+         * converting to/from Base64 notation.
+         * When encoding, bytes are buffered three
+         * at a time before the output stream actually
+         * gets a write() call.
+         * When decoding, bytes are buffered four
+         * at a time.
+         *
+         * @param theByte the byte to write
+         * @since 1.3
+         */
+        public void write(int theByte) throws java.io.IOException
+        {
+            // Encoding suspended?
+            if( suspendEncoding )
+            {
+                super.out.write( theByte );
+                return;
+            }   // end if: supsended
+
+            // Encode?
+            if( encode )
+            {
+                buffer[ position++ ] = (byte)theByte;
+                if( position >= bufferLength )  // Enough to encode.
+                {
+                    out.write( encode3to4( b4, buffer, bufferLength, options ) );
+
+                    lineLength += 4;
+                    if( breakLines && lineLength >= MAX_LINE_LENGTH )
+                    {
+                        out.write( NEW_LINE );
+                        lineLength = 0;
+                    }   // end if: end of line
+
+                    position = 0;
+                }   // end if: enough to output
+            }   // end if: encoding
+
+            // Else, Decoding
+            else
+            {
+                // Meaningful Base64 character?
+                if( decodabet[ theByte & 0x7f ] > WHITE_SPACE_ENC )
+                {
+                    buffer[ position++ ] = (byte)theByte;
+                    if( position >= bufferLength )  // Enough to output.
+                    {
+                        int len = Base64.decode4to3( buffer, 0, b4, 0, options );
+                        out.write( b4, 0, len );
+                        //out.write( Base64.decode4to3( buffer ) );
+                        position = 0;
+                    }   // end if: enough to output
+                }   // end if: meaningful base64 character
+                else if( decodabet[ theByte & 0x7f ] != WHITE_SPACE_ENC )
+                {
+                    throw new java.io.IOException( "Invalid character in Base64 data." );
+                }   // end else: not white space either
+            }   // end else: decoding
+        }   // end write
+
+
+
+        /**
+         * Calls {@link #write(int)} repeatedly until <var>len</var>
+         * bytes are written.
+         *
+         * @param theBytes array from which to read bytes
+         * @param off offset for array
+         * @param len max number of bytes to read into array
+         * @since 1.3
+         */
+        public void write( byte[] theBytes, int off, int len ) throws java.io.IOException
+        {
+            // Encoding suspended?
+            if( suspendEncoding )
+            {
+                super.out.write( theBytes, off, len );
+                return;
+            }   // end if: supsended
+
+            for( int i = 0; i < len; i++ )
+            {
+                write( theBytes[ off + i ] );
+            }   // end for: each byte written
+
+        }   // end write
+
+
+
+        /**
+         * Method added by PHIL. [Thanks, PHIL. -Rob]
+         * This pads the buffer without closing the stream.
+         */
+        public void flushBase64() throws java.io.IOException
+        {
+            if( position > 0 )
+            {
+                if( encode )
+                {
+                    out.write( encode3to4( b4, buffer, position, options ) );
+                    position = 0;
+                }   // end if: encoding
+                else
+                {
+                    throw new java.io.IOException( "Base64 input not properly padded." );
+                }   // end else: decoding
+            }   // end if: buffer partially full
+
+        }   // end flush
+
+
+        /**
+         * Flushes and closes (I think, in the superclass) the stream.
+         *
+         * @since 1.3
+         */
+        public void close() throws java.io.IOException
+        {
+            // 1. Ensure that pending characters are written
+            flushBase64();
+
+            // 2. Actually close the stream
+            // Base class both flushes and closes.
+            super.close();
+
+            buffer = null;
+            out    = null;
+        }   // end close
+
+
+
+        /**
+         * Suspends encoding of the stream.
+         * May be helpful if you need to embed a piece of
+         * base640-encoded data in a stream.
+         *
+         * @since 1.5.1
+         */
+        public void suspendEncoding() throws java.io.IOException
+        {
+            flushBase64();
+            this.suspendEncoding = true;
+        }   // end suspendEncoding
+
+
+        /**
+         * Resumes encoding of the stream.
+         * May be helpful if you need to embed a piece of
+         * base640-encoded data in a stream.
+         *
+         * @since 1.5.1
+         */
+        public void resumeEncoding()
+        {
+            this.suspendEncoding = false;
+        }   // end resumeEncoding
+
+
+
+    }   // end inner class OutputStream
+
+
+}   // end class Base64
+
diff --git a/src/org/jivesoftware/smack/util/Base64Encoder.java b/src/org/jivesoftware/smack/util/Base64Encoder.java
new file mode 100644
index 0000000..d53c0ed
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/Base64Encoder.java
@@ -0,0 +1,42 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+
+/**
+ * A Base 64 encoding implementation.
+ * @author Florian Schmaus
+ */
+public class Base64Encoder implements StringEncoder {
+
+    private static Base64Encoder instance = new Base64Encoder();
+
+    private Base64Encoder() {
+        // Use getInstance()
+    }
+
+    public static Base64Encoder getInstance() {
+        return instance;
+    }
+
+    public String encode(String s) {
+        return Base64.encodeBytes(s.getBytes());
+    }
+
+    public String decode(String s) {
+        return new String(Base64.decode(s));
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/Base64FileUrlEncoder.java b/src/org/jivesoftware/smack/util/Base64FileUrlEncoder.java
new file mode 100644
index 0000000..190b374
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/Base64FileUrlEncoder.java
@@ -0,0 +1,48 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+
+/**
+ * A Base 64 encoding implementation that generates filename and Url safe encodings.
+ * 
+ * <p>
+ * Note: This does NOT produce standard Base 64 encodings, but a variant as defined in 
+ * Section 4 of RFC3548:
+ * <a href="http://www.faqs.org/rfcs/rfc3548.html">http://www.faqs.org/rfcs/rfc3548.html</a>.
+ * 
+ * @author Robin Collier
+ */
+public class Base64FileUrlEncoder implements StringEncoder {
+
+    private static Base64FileUrlEncoder instance = new Base64FileUrlEncoder();
+
+    private Base64FileUrlEncoder() {
+        // Use getInstance()
+    }
+
+    public static Base64FileUrlEncoder getInstance() {
+        return instance;
+    }
+
+    public String encode(String s) {
+        return Base64.encodeBytes(s.getBytes(), Base64.URL_SAFE);
+    }
+
+    public String decode(String s) {
+        return new String(Base64.decode(s, Base64.URL_SAFE));
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/Cache.java b/src/org/jivesoftware/smack/util/Cache.java
new file mode 100644
index 0000000..964ac23
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/Cache.java
@@ -0,0 +1,678 @@
+/**
+ * $Revision: 1456 $
+ * $Date: 2005-06-01 22:04:54 -0700 (Wed, 01 Jun 2005) $
+ *
+ * Copyright 2003-2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import org.jivesoftware.smack.util.collections.AbstractMapEntry;
+
+import java.util.*;
+
+/**
+ * A specialized Map that is size-limited (using an LRU algorithm) and
+ * has an optional expiration time for cache items. The Map is thread-safe.<p>
+ *
+ * The algorithm for cache is as follows: a HashMap is maintained for fast
+ * object lookup. Two linked lists are maintained: one keeps objects in the
+ * order they are accessed from cache, the other keeps objects in the order
+ * they were originally added to cache. When objects are added to cache, they
+ * are first wrapped by a CacheObject which maintains the following pieces
+ * of information:<ul>
+ * <li> A pointer to the node in the linked list that maintains accessed
+ * order for the object. Keeping a reference to the node lets us avoid
+ * linear scans of the linked list.
+ * <li> A pointer to the node in the linked list that maintains the age
+ * of the object in cache. Keeping a reference to the node lets us avoid
+ * linear scans of the linked list.</ul>
+ * <p/>
+ * To get an object from cache, a hash lookup is performed to get a reference
+ * to the CacheObject that wraps the real object we are looking for.
+ * The object is subsequently moved to the front of the accessed linked list
+ * and any necessary cache cleanups are performed. Cache deletion and expiration
+ * is performed as needed.
+ *
+ * @author Matt Tucker
+ */
+public class Cache<K, V> implements Map<K, V> {
+
+    /**
+     * The map the keys and values are stored in.
+     */
+    protected Map<K, CacheObject<V>> map;
+
+    /**
+     * Linked list to maintain order that cache objects are accessed
+     * in, most used to least used.
+     */
+    protected LinkedList lastAccessedList;
+
+    /**
+     * Linked list to maintain time that cache objects were initially added
+     * to the cache, most recently added to oldest added.
+     */
+    protected LinkedList ageList;
+
+    /**
+     * Maximum number of items the cache will hold.
+     */
+    protected int maxCacheSize;
+
+    /**
+     * Maximum length of time objects can exist in cache before expiring.
+     */
+    protected long maxLifetime;
+
+    /**
+     * Maintain the number of cache hits and misses. A cache hit occurs every
+     * time the get method is called and the cache contains the requested
+     * object. A cache miss represents the opposite occurence.<p>
+     *
+     * Keeping track of cache hits and misses lets one measure how efficient
+     * the cache is; the higher the percentage of hits, the more efficient.
+     */
+    protected long cacheHits, cacheMisses = 0L;
+
+    /**
+     * Create a new cache and specify the maximum size of for the cache in
+     * bytes, and the maximum lifetime of objects.
+     *
+     * @param maxSize the maximum number of objects the cache will hold. -1
+     *      means the cache has no max size.
+     * @param maxLifetime the maximum amount of time (in ms) objects can exist in
+     *      cache before being deleted. -1 means objects never expire.
+     */
+    public Cache(int maxSize, long maxLifetime) {
+        if (maxSize == 0) {
+            throw new IllegalArgumentException("Max cache size cannot be 0.");
+        }
+        this.maxCacheSize = maxSize;
+        this.maxLifetime = maxLifetime;
+
+        // Our primary data structure is a hash map. The default capacity of 11
+        // is too small in almost all cases, so we set it bigger.
+        map = new HashMap<K, CacheObject<V>>(103);
+
+        lastAccessedList = new LinkedList();
+        ageList = new LinkedList();
+    }
+
+    public synchronized V put(K key, V value) {
+        V oldValue = null;
+        // Delete an old entry if it exists.
+        if (map.containsKey(key)) {
+            oldValue = remove(key, true);
+        }
+
+        CacheObject<V> cacheObject = new CacheObject<V>(value);
+        map.put(key, cacheObject);
+        // Make an entry into the cache order list.
+        // Store the cache order list entry so that we can get back to it
+        // during later lookups.
+        cacheObject.lastAccessedListNode = lastAccessedList.addFirst(key);
+        // Add the object to the age list
+        LinkedListNode ageNode = ageList.addFirst(key);
+        ageNode.timestamp = System.currentTimeMillis();
+        cacheObject.ageListNode = ageNode;
+
+        // If cache is too full, remove least used cache entries until it is not too full.
+        cullCache();
+
+        return oldValue;
+    }
+
+    public synchronized V get(Object key) {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        CacheObject<V> cacheObject = map.get(key);
+        if (cacheObject == null) {
+            // The object didn't exist in cache, so increment cache misses.
+            cacheMisses++;
+            return null;
+        }
+        // Remove the object from it's current place in the cache order list,
+        // and re-insert it at the front of the list.
+        cacheObject.lastAccessedListNode.remove();
+        lastAccessedList.addFirst(cacheObject.lastAccessedListNode);
+
+        // The object exists in cache, so increment cache hits. Also, increment
+        // the object's read count.
+        cacheHits++;
+        cacheObject.readCount++;
+
+        return cacheObject.object;
+    }
+
+    public synchronized V remove(Object key) {
+        return remove(key, false);
+    }
+
+    /*
+     * Remove operation with a flag so we can tell coherence if the remove was
+     * caused by cache internal processing such as eviction or loading
+     */
+    public synchronized V remove(Object key, boolean internal) {
+        //noinspection SuspiciousMethodCalls
+        CacheObject<V> cacheObject =  map.remove(key);
+        // If the object is not in cache, stop trying to remove it.
+        if (cacheObject == null) {
+            return null;
+        }
+        // Remove from the cache order list
+        cacheObject.lastAccessedListNode.remove();
+        cacheObject.ageListNode.remove();
+        // Remove references to linked list nodes
+        cacheObject.ageListNode = null;
+        cacheObject.lastAccessedListNode = null;
+
+        return cacheObject.object;
+    }
+
+    public synchronized void clear() {
+        Object[] keys = map.keySet().toArray();
+        for (Object key : keys) {
+            remove(key);
+        }
+
+        // Now, reset all containers.
+        map.clear();
+        lastAccessedList.clear();
+        ageList.clear();
+
+        cacheHits = 0;
+        cacheMisses = 0;
+    }
+
+    public synchronized int size() {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return map.size();
+    }
+
+    public synchronized boolean isEmpty() {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return map.isEmpty();
+    }
+
+    public synchronized Collection<V> values() {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return Collections.unmodifiableCollection(new AbstractCollection<V>() {
+            Collection<CacheObject<V>> values = map.values();
+            public Iterator<V> iterator() {
+                return new Iterator<V>() {
+                    Iterator<CacheObject<V>> it = values.iterator();
+
+                    public boolean hasNext() {
+                        return it.hasNext();
+                    }
+
+                    public V next() {
+                        return it.next().object;
+                    }
+
+                    public void remove() {
+                        it.remove();
+                    }
+                };
+            }
+
+            public int size() {
+                return values.size();
+            }
+        });
+    }
+
+    public synchronized boolean containsKey(Object key) {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return map.containsKey(key);
+    }
+
+    public void putAll(Map<? extends K, ? extends V> map) {
+        for (Entry<? extends K, ? extends V> entry : map.entrySet()) {
+            V value = entry.getValue();
+            // If the map is another DefaultCache instance than the
+            // entry values will be CacheObject instances that need
+            // to be converted to the normal object form.
+            if (value instanceof CacheObject) {
+                //noinspection unchecked
+                value = ((CacheObject<V>) value).object;
+            }
+            put(entry.getKey(), value);
+        }
+    }
+
+    public synchronized boolean containsValue(Object value) {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        //noinspection unchecked
+        CacheObject<V> cacheObject = new CacheObject<V>((V) value);
+
+        return map.containsValue(cacheObject);
+    }
+
+    public synchronized Set<Map.Entry<K, V>> entrySet() {
+        // Warning -- this method returns CacheObject instances and not Objects
+        // in the same form they were put into cache.
+
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return new AbstractSet<Map.Entry<K, V>>() {
+            private final Set<Map.Entry<K, CacheObject<V>>> set = map.entrySet();
+
+            public Iterator<Entry<K, V>> iterator() {
+                return new Iterator<Entry<K, V>>() {
+                    private final Iterator<Entry<K, CacheObject<V>>> it = set.iterator();
+                    public boolean hasNext() {
+                        return it.hasNext();
+                    }
+
+                    public Entry<K, V> next() {
+                        Map.Entry<K, CacheObject<V>> entry = it.next();
+                        return new AbstractMapEntry<K, V>(entry.getKey(), entry.getValue().object) {
+                            @Override
+                            public V setValue(V value) {
+                                throw new UnsupportedOperationException("Cannot set");
+                            }
+                        };
+                    }
+
+                    public void remove() {
+                        it.remove();
+                    }
+                };
+
+            }
+
+            public int size() {
+                return set.size();
+            }
+        };
+    }
+
+    public synchronized Set<K> keySet() {
+        // First, clear all entries that have been in cache longer than the
+        // maximum defined age.
+        deleteExpiredEntries();
+
+        return Collections.unmodifiableSet(map.keySet());
+    }
+
+    public long getCacheHits() {
+        return cacheHits;
+    }
+
+    public long getCacheMisses() {
+        return cacheMisses;
+    }
+
+    public int getMaxCacheSize() {
+        return maxCacheSize;
+    }
+
+    public synchronized void setMaxCacheSize(int maxCacheSize) {
+        this.maxCacheSize = maxCacheSize;
+        // It's possible that the new max size is smaller than our current cache
+        // size. If so, we need to delete infrequently used items.
+        cullCache();
+    }
+
+    public long getMaxLifetime() {
+        return maxLifetime;
+    }
+
+    public void setMaxLifetime(long maxLifetime) {
+        this.maxLifetime = maxLifetime;
+    }
+
+    /**
+     * Clears all entries out of cache where the entries are older than the
+     * maximum defined age.
+     */
+    protected synchronized void deleteExpiredEntries() {
+        // Check if expiration is turned on.
+        if (maxLifetime <= 0) {
+            return;
+        }
+
+        // Remove all old entries. To do this, we remove objects from the end
+        // of the linked list until they are no longer too old. We get to avoid
+        // any hash lookups or looking at any more objects than is strictly
+        // neccessary.
+        LinkedListNode node = ageList.getLast();
+        // If there are no entries in the age list, return.
+        if (node == null) {
+            return;
+        }
+
+        // Determine the expireTime, which is the moment in time that elements
+        // should expire from cache. Then, we can do an easy check to see
+        // if the expire time is greater than the expire time.
+        long expireTime = System.currentTimeMillis() - maxLifetime;
+
+        while (expireTime > node.timestamp) {
+            if (remove(node.object, true) == null) {
+                System.err.println("Error attempting to remove(" + node.object.toString() +
+                ") - cacheObject not found in cache!");
+                // remove from the ageList
+                node.remove();
+            }
+
+            // Get the next node.
+            node = ageList.getLast();
+            // If there are no more entries in the age list, return.
+            if (node == null) {
+                return;
+            }
+        }
+    }
+
+    /**
+     * Removes the least recently used elements if the cache size is greater than
+     * or equal to the maximum allowed size until the cache is at least 10% empty.
+     */
+    protected synchronized void cullCache() {
+        // Check if a max cache size is defined.
+        if (maxCacheSize < 0) {
+            return;
+        }
+
+        // See if the cache is too big. If so, clean out cache until it's 10% free.
+        if (map.size() > maxCacheSize) {
+            // First, delete any old entries to see how much memory that frees.
+            deleteExpiredEntries();
+            // Next, delete the least recently used elements until 10% of the cache
+            // has been freed.
+            int desiredSize = (int) (maxCacheSize * .90);
+            for (int i=map.size(); i>desiredSize; i--) {
+                // Get the key and invoke the remove method on it.
+                if (remove(lastAccessedList.getLast().object, true) == null) {
+                    System.err.println("Error attempting to cullCache with remove(" +
+                            lastAccessedList.getLast().object.toString() + ") - " +
+                            "cacheObject not found in cache!");
+                    lastAccessedList.getLast().remove();
+                }
+            }
+        }
+    }
+
+    /**
+     * Wrapper for all objects put into cache. It's primary purpose is to maintain
+     * references to the linked lists that maintain the creation time of the object
+     * and the ordering of the most used objects.
+     *
+     * This class is optimized for speed rather than strictly correct encapsulation.
+     */
+    private static class CacheObject<V> {
+
+       /**
+        * Underlying object wrapped by the CacheObject.
+        */
+        public V object;
+
+        /**
+         * A reference to the node in the cache order list. We keep the reference
+         * here to avoid linear scans of the list. Every time the object is
+         * accessed, the node is removed from its current spot in the list and
+         * moved to the front.
+         */
+        public LinkedListNode lastAccessedListNode;
+
+        /**
+         * A reference to the node in the age order list. We keep the reference
+         * here to avoid linear scans of the list. The reference is used if the
+         * object has to be deleted from the list.
+         */
+        public LinkedListNode ageListNode;
+
+        /**
+         * A count of the number of times the object has been read from cache.
+         */
+        public int readCount = 0;
+
+        /**
+         * Creates a new cache object wrapper.
+         *
+         * @param object the underlying Object to wrap.
+         */
+        public CacheObject(V object) {
+            this.object = object;
+        }
+
+        public boolean equals(Object o) {
+            if (this == o) {
+                return true;
+            }
+            if (!(o instanceof CacheObject)) {
+                return false;
+            }
+
+            final CacheObject<?> cacheObject = (CacheObject<?>) o;
+
+            return object.equals(cacheObject.object);
+
+        }
+
+        public int hashCode() {
+            return object.hashCode();
+        }
+    }
+
+    /**
+     * Simple LinkedList implementation. The main feature is that list nodes
+     * are public, which allows very fast delete operations when one has a
+     * reference to the node that is to be deleted.<p>
+     */
+    private static class LinkedList {
+
+        /**
+         * The root of the list keeps a reference to both the first and last
+         * elements of the list.
+         */
+        private LinkedListNode head = new LinkedListNode("head", null, null);
+
+        /**
+         * Creates a new linked list.
+         */
+        public LinkedList() {
+            head.next = head.previous = head;
+        }
+
+        /**
+         * Returns the first linked list node in the list.
+         *
+         * @return the first element of the list.
+         */
+        public LinkedListNode getFirst() {
+            LinkedListNode node = head.next;
+            if (node == head) {
+                return null;
+            }
+            return node;
+        }
+
+        /**
+         * Returns the last linked list node in the list.
+         *
+         * @return the last element of the list.
+         */
+        public LinkedListNode getLast() {
+            LinkedListNode node = head.previous;
+            if (node == head) {
+                return null;
+            }
+            return node;
+        }
+
+        /**
+         * Adds a node to the beginning of the list.
+         *
+         * @param node the node to add to the beginning of the list.
+         * @return the node
+         */
+        public LinkedListNode addFirst(LinkedListNode node) {
+            node.next = head.next;
+            node.previous = head;
+            node.previous.next = node;
+            node.next.previous = node;
+            return node;
+        }
+
+        /**
+         * Adds an object to the beginning of the list by automatically creating a
+         * a new node and adding it to the beginning of the list.
+         *
+         * @param object the object to add to the beginning of the list.
+         * @return the node created to wrap the object.
+         */
+        public LinkedListNode addFirst(Object object) {
+            LinkedListNode node = new LinkedListNode(object, head.next, head);
+            node.previous.next = node;
+            node.next.previous = node;
+            return node;
+        }
+
+        /**
+         * Adds an object to the end of the list by automatically creating a
+         * a new node and adding it to the end of the list.
+         *
+         * @param object the object to add to the end of the list.
+         * @return the node created to wrap the object.
+         */
+        public LinkedListNode addLast(Object object) {
+            LinkedListNode node = new LinkedListNode(object, head, head.previous);
+            node.previous.next = node;
+            node.next.previous = node;
+            return node;
+        }
+
+        /**
+         * Erases all elements in the list and re-initializes it.
+         */
+        public void clear() {
+            //Remove all references in the list.
+            LinkedListNode node = getLast();
+            while (node != null) {
+                node.remove();
+                node = getLast();
+            }
+
+            //Re-initialize.
+            head.next = head.previous = head;
+        }
+
+        /**
+         * Returns a String representation of the linked list with a comma
+         * delimited list of all the elements in the list.
+         *
+         * @return a String representation of the LinkedList.
+         */
+        public String toString() {
+            LinkedListNode node = head.next;
+            StringBuilder buf = new StringBuilder();
+            while (node != head) {
+                buf.append(node.toString()).append(", ");
+                node = node.next;
+            }
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Doubly linked node in a LinkedList. Most LinkedList implementations keep the
+     * equivalent of this class private. We make it public so that references
+     * to each node in the list can be maintained externally.
+     *
+     * Exposing this class lets us make remove operations very fast. Remove is
+     * built into this class and only requires two reference reassignments. If
+     * remove existed in the main LinkedList class, a linear scan would have to
+     * be performed to find the correct node to delete.
+     *
+     * The linked list implementation was specifically written for the Jive
+     * cache system. While it can be used as a general purpose linked list, for
+     * most applications, it is more suitable to use the linked list that is part
+     * of the Java Collections package.
+     */
+    private static class LinkedListNode {
+
+        public LinkedListNode previous;
+        public LinkedListNode next;
+        public Object object;
+
+        /**
+         * This class is further customized for the Jive cache system. It
+         * maintains a timestamp of when a Cacheable object was first added to
+         * cache. Timestamps are stored as long values and represent the number
+         * of milliseconds passed since January 1, 1970 00:00:00.000 GMT.<p>
+         *
+         * The creation timestamp is used in the case that the cache has a
+         * maximum lifetime set. In that case, when
+         * [current time] - [creation time] > [max lifetime], the object will be
+         * deleted from cache.
+         */
+        public long timestamp;
+
+        /**
+         * Constructs a new linked list node.
+         *
+         * @param object the Object that the node represents.
+         * @param next a reference to the next LinkedListNode in the list.
+         * @param previous a reference to the previous LinkedListNode in the list.
+         */
+        public LinkedListNode(Object object, LinkedListNode next,
+                LinkedListNode previous)
+        {
+            this.object = object;
+            this.next = next;
+            this.previous = previous;
+        }
+
+        /**
+         * Removes this node from the linked list that it is a part of.
+         */
+        public void remove() {
+            previous.next = next;
+            next.previous = previous;
+        }
+
+        /**
+         * Returns a String representation of the linked list node by calling the
+         * toString method of the node's object.
+         *
+         * @return a String representation of the LinkedListNode.
+         */
+        public String toString() {
+            return object.toString();
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/util/DNSUtil.java b/src/org/jivesoftware/smack/util/DNSUtil.java
new file mode 100644
index 0000000..628d8e8
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/DNSUtil.java
@@ -0,0 +1,229 @@
+/**
+ * $Revision: 1456 $
+ * $Date: 2005-06-01 22:04:54 -0700 (Wed, 01 Jun 2005) $
+ *
+ * Copyright 2003-2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.SortedMap;
+import java.util.TreeMap;
+
+import org.jivesoftware.smack.util.dns.DNSResolver;
+import org.jivesoftware.smack.util.dns.HostAddress;
+import org.jivesoftware.smack.util.dns.SRVRecord;
+
+/**
+ * Utility class to perform DNS lookups for XMPP services.
+ *
+ * @author Matt Tucker
+ */
+public class DNSUtil {
+
+    /**
+     * Create a cache to hold the 100 most recently accessed DNS lookups for a period of
+     * 10 minutes.
+     */
+    private static Map<String, List<HostAddress>> cache = new Cache<String, List<HostAddress>>(100, 1000*60*10);
+
+    private static DNSResolver dnsResolver = null;
+
+    /**
+     * Set the DNS resolver that should be used to perform DNS lookups.
+     *
+     * @param resolver
+     */
+    public static void setDNSResolver(DNSResolver resolver) {
+        dnsResolver = resolver;
+    }
+
+    /**
+     * Returns the current DNS resolved used to perform DNS lookups.
+     *
+     * @return
+     */
+    public static DNSResolver getDNSResolver() {
+        return dnsResolver;
+    }
+
+    /**
+     * Returns a list of HostAddresses under which the specified XMPP server can be
+     * reached at for client-to-server communication. A DNS lookup for a SRV
+     * record in the form "_xmpp-client._tcp.example.com" is attempted, according
+     * to section 14.4 of RFC 3920. If that lookup fails, a lookup in the older form
+     * of "_jabber._tcp.example.com" is attempted since servers that implement an
+     * older version of the protocol may be listed using that notation. If that
+     * lookup fails as well, it's assumed that the XMPP server lives at the
+     * host resolved by a DNS lookup at the specified domain on the default port
+     * of 5222.<p>
+     *
+     * As an example, a lookup for "example.com" may return "im.example.com:5269".
+     *
+     * @param domain the domain.
+     * @return List of HostAddress, which encompasses the hostname and port that the
+     *      XMPP server can be reached at for the specified domain.
+     */
+    public static List<HostAddress> resolveXMPPDomain(String domain) {
+        return resolveDomain(domain, 'c');
+    }
+
+    /**
+     * Returns a list of HostAddresses under which the specified XMPP server can be
+     * reached at for server-to-server communication. A DNS lookup for a SRV
+     * record in the form "_xmpp-server._tcp.example.com" is attempted, according
+     * to section 14.4 of RFC 3920. If that lookup fails, a lookup in the older form
+     * of "_jabber._tcp.example.com" is attempted since servers that implement an
+     * older version of the protocol may be listed using that notation. If that
+     * lookup fails as well, it's assumed that the XMPP server lives at the
+     * host resolved by a DNS lookup at the specified domain on the default port
+     * of 5269.<p>
+     *
+     * As an example, a lookup for "example.com" may return "im.example.com:5269".
+     *
+     * @param domain the domain.
+     * @return List of HostAddress, which encompasses the hostname and port that the
+     *      XMPP server can be reached at for the specified domain.
+     */
+    public static List<HostAddress> resolveXMPPServerDomain(String domain) {
+        return resolveDomain(domain, 's');
+    }
+
+    private static List<HostAddress> resolveDomain(String domain, char keyPrefix) {
+        // Prefix the key with 's' to distinguish him from the client domain lookups
+        String key = keyPrefix + domain;
+        // Return item from cache if it exists.
+        if (cache.containsKey(key)) {
+            List<HostAddress> addresses = cache.get(key);
+            if (addresses != null) {
+                return addresses;
+            }
+        }
+
+        if (dnsResolver == null)
+            throw new IllegalStateException("No DNS resolver active.");
+
+        List<HostAddress> addresses = new ArrayList<HostAddress>();
+
+        // Step one: Do SRV lookups
+        String srvDomain;
+        if (keyPrefix == 's') {
+            srvDomain = "_xmpp-server._tcp." + domain;
+        } else if (keyPrefix == 'c') {
+            srvDomain = "_xmpp-client._tcp." + domain;
+        } else {
+            srvDomain = domain;
+        }
+        List<SRVRecord> srvRecords = dnsResolver.lookupSRVRecords(srvDomain);
+        List<HostAddress> sortedRecords = sortSRVRecords(srvRecords);
+        if (sortedRecords != null)
+            addresses.addAll(sortedRecords);
+
+        // Step two: Add the hostname to the end of the list
+        addresses.add(new HostAddress(domain));
+
+        // Add item to cache.
+        cache.put(key, addresses);
+
+        return addresses;
+    }
+
+    /**
+     * Sort a given list of SRVRecords as described in RFC 2782
+     * Note that we follow the RFC with one exception. In a group of the same priority, only the first entry
+     * is calculated by random. The others are ore simply ordered by their priority.
+     * 
+     * @param records
+     * @return
+     */
+    protected static List<HostAddress> sortSRVRecords(List<SRVRecord> records) {
+        // RFC 2782, Usage rules: "If there is precisely one SRV RR, and its Target is "."
+        // (the root domain), abort."
+        if (records.size() == 1 && records.get(0).getFQDN().equals("."))
+            return null;
+
+        // sorting the records improves the performance of the bisection later
+        Collections.sort(records);
+
+        // create the priority buckets
+        SortedMap<Integer, List<SRVRecord>> buckets = new TreeMap<Integer, List<SRVRecord>>();
+        for (SRVRecord r : records) {
+            Integer priority = r.getPriority();
+            List<SRVRecord> bucket = buckets.get(priority);
+            // create the list of SRVRecords if it doesn't exist
+            if (bucket == null) {
+                bucket = new LinkedList<SRVRecord>();
+                buckets.put(priority, bucket);
+            }
+            bucket.add(r);
+        }
+
+        List<HostAddress> res = new ArrayList<HostAddress>(records.size());
+
+        for (Integer priority : buckets.keySet()) {
+            List<SRVRecord> bucket = buckets.get(priority);
+            int bucketSize;
+            while ((bucketSize = bucket.size()) > 0) {
+                int[] totals = new int[bucket.size()];
+                int running_total = 0;
+                int count = 0;
+                int zeroWeight = 1;
+
+                for (SRVRecord r : bucket) {
+                    if (r.getWeight() > 0)
+                        zeroWeight = 0;
+                }
+
+                for (SRVRecord r : bucket) {
+                    running_total += (r.getWeight() + zeroWeight);
+                    totals[count] = running_total;
+                    count++;
+                }
+                int selectedPos;
+                if (running_total == 0) {
+                    // If running total is 0, then all weights in this priority
+                    // group are 0. So we simply select one of the weights randomly
+                    // as the other 'normal' algorithm is unable to handle this case
+                    selectedPos = (int) (Math.random() * bucketSize);
+                } else {
+                    double rnd = Math.random() * running_total;
+                    selectedPos = bisect(totals, rnd);
+                } 
+                // add the SRVRecord that was randomly chosen on it's weight
+                // to the start of the result list
+                SRVRecord chosenSRVRecord = bucket.remove(selectedPos);
+                res.add(chosenSRVRecord);
+            }
+        }
+
+        return res;
+    }
+
+    // TODO this is not yet really bisection just a stupid linear search
+    private static int bisect(int[] array, double value) {
+        int pos = 0;
+        for (int element : array) {
+            if (value < element)
+                break;
+            pos++;
+        }
+        return pos;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smack/util/DateFormatType.java b/src/org/jivesoftware/smack/util/DateFormatType.java
new file mode 100644
index 0000000..9253038
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/DateFormatType.java
@@ -0,0 +1,65 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2013 Robin Collier.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util;
+
+import java.text.SimpleDateFormat;
+
+/**
+ * Defines the various date and time profiles used in XMPP along with their associated formats.
+ * 
+ * @author Robin Collier
+ * 
+ */
+public enum DateFormatType {
+    // @formatter:off
+    XEP_0082_DATE_PROFILE("yyyy-MM-dd"), 
+    XEP_0082_DATETIME_PROFILE("yyyy-MM-dd'T'HH:mm:ssZ"), 
+    XEP_0082_DATETIME_MILLIS_PROFILE("yyyy-MM-dd'T'HH:mm:ss.SSSZ"), 
+    XEP_0082_TIME_PROFILE("hh:mm:ss"), 
+    XEP_0082_TIME_ZONE_PROFILE("hh:mm:ssZ"), 
+    XEP_0082_TIME_MILLIS_PROFILE("hh:mm:ss.SSS"), 
+    XEP_0082_TIME_MILLIS_ZONE_PROFILE("hh:mm:ss.SSSZ"), 
+    XEP_0091_DATETIME("yyyyMMdd'T'HH:mm:ss");
+    // @formatter:on
+
+    private String formatString;
+
+    private DateFormatType(String dateFormat) {
+        formatString = dateFormat;
+    }
+
+    /**
+     * Get the format string as defined in either XEP-0082 or XEP-0091.
+     * 
+     * @return The defined string format for the date.
+     */
+    public String getFormatString() {
+        return formatString;
+    }
+
+    /**
+     * Create a {@link SimpleDateFormat} object with the format defined by {@link #getFormatString()}.
+     * 
+     * @return A new date formatter.
+     */
+    public SimpleDateFormat createFormatter() {
+        return new SimpleDateFormat(getFormatString());
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/ObservableReader.java b/src/org/jivesoftware/smack/util/ObservableReader.java
new file mode 100644
index 0000000..8c64508
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/ObservableReader.java
@@ -0,0 +1,118 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * An ObservableReader is a wrapper on a Reader that notifies to its listeners when
+ * reading character streams.
+ * 
+ * @author Gaston Dombiak
+ */
+public class ObservableReader extends Reader {
+
+    Reader wrappedReader = null;
+    List<ReaderListener> listeners = new ArrayList<ReaderListener>();
+
+    public ObservableReader(Reader wrappedReader) {
+        this.wrappedReader = wrappedReader;
+    }
+        
+    public int read(char[] cbuf, int off, int len) throws IOException {
+        int count = wrappedReader.read(cbuf, off, len);
+        if (count > 0) {
+            String str = new String(cbuf, off, count);
+            // Notify that a new string has been read
+            ReaderListener[] readerListeners = null;
+            synchronized (listeners) {
+                readerListeners = new ReaderListener[listeners.size()];
+                listeners.toArray(readerListeners);
+            }
+            for (int i = 0; i < readerListeners.length; i++) {
+                readerListeners[i].read(str);
+            }
+        }
+        return count;
+    }
+
+    public void close() throws IOException {
+        wrappedReader.close();
+    }
+
+    public int read() throws IOException {
+        return wrappedReader.read();
+    }
+
+    public int read(char cbuf[]) throws IOException {
+        return wrappedReader.read(cbuf);
+    }
+
+    public long skip(long n) throws IOException {
+        return wrappedReader.skip(n);
+    }
+
+    public boolean ready() throws IOException {
+        return wrappedReader.ready();
+    }
+
+    public boolean markSupported() {
+        return wrappedReader.markSupported();
+    }
+
+    public void mark(int readAheadLimit) throws IOException {
+        wrappedReader.mark(readAheadLimit);
+    }
+
+    public void reset() throws IOException {
+        wrappedReader.reset();
+    }
+
+    /**
+     * Adds a reader listener to this reader that will be notified when
+     * new strings are read.
+     *
+     * @param readerListener a reader listener.
+     */
+    public void addReaderListener(ReaderListener readerListener) {
+        if (readerListener == null) {
+            return;
+        }
+        synchronized (listeners) {
+            if (!listeners.contains(readerListener)) {
+                listeners.add(readerListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a reader listener from this reader.
+     *
+     * @param readerListener a reader listener.
+     */
+    public void removeReaderListener(ReaderListener readerListener) {
+        synchronized (listeners) {
+            listeners.remove(readerListener);
+        }
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/ObservableWriter.java b/src/org/jivesoftware/smack/util/ObservableWriter.java
new file mode 100644
index 0000000..90cabb6
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/ObservableWriter.java
@@ -0,0 +1,120 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * An ObservableWriter is a wrapper on a Writer that notifies to its listeners when
+ * writing to character streams.
+ * 
+ * @author Gaston Dombiak
+ */
+public class ObservableWriter extends Writer {
+
+    Writer wrappedWriter = null;
+    List<WriterListener> listeners = new ArrayList<WriterListener>();
+
+    public ObservableWriter(Writer wrappedWriter) {
+        this.wrappedWriter = wrappedWriter;
+    }
+
+    public void write(char cbuf[], int off, int len) throws IOException {
+        wrappedWriter.write(cbuf, off, len);
+        String str = new String(cbuf, off, len);
+        notifyListeners(str);
+    }
+
+    public void flush() throws IOException {
+        wrappedWriter.flush();
+    }
+
+    public void close() throws IOException {
+        wrappedWriter.close();
+    }
+
+    public void write(int c) throws IOException {
+        wrappedWriter.write(c);
+    }
+
+    public void write(char cbuf[]) throws IOException {
+        wrappedWriter.write(cbuf);
+        String str = new String(cbuf);
+        notifyListeners(str);
+    }
+
+    public void write(String str) throws IOException {
+        wrappedWriter.write(str);
+        notifyListeners(str);
+    }
+
+    public void write(String str, int off, int len) throws IOException {
+        wrappedWriter.write(str, off, len);
+        str = str.substring(off, off + len);
+        notifyListeners(str);
+    }
+
+    /**
+     * Notify that a new string has been written.
+     * 
+     * @param str the written String to notify 
+     */
+    private void notifyListeners(String str) {
+        WriterListener[] writerListeners = null;
+        synchronized (listeners) {
+            writerListeners = new WriterListener[listeners.size()];
+            listeners.toArray(writerListeners);
+        }
+        for (int i = 0; i < writerListeners.length; i++) {
+            writerListeners[i].write(str);
+        }
+    }
+
+    /**
+     * Adds a writer listener to this writer that will be notified when
+     * new strings are sent.
+     *
+     * @param writerListener a writer listener.
+     */
+    public void addWriterListener(WriterListener writerListener) {
+        if (writerListener == null) {
+            return;
+        }
+        synchronized (listeners) {
+            if (!listeners.contains(writerListener)) {
+                listeners.add(writerListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a writer listener from this writer.
+     *
+     * @param writerListener a writer listener.
+     */
+    public void removeWriterListener(WriterListener writerListener) {
+        synchronized (listeners) {
+            listeners.remove(writerListener);
+        }
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/PacketParserUtils.java b/src/org/jivesoftware/smack/util/PacketParserUtils.java
new file mode 100644
index 0000000..aacbad5
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/PacketParserUtils.java
@@ -0,0 +1,925 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.Authentication;
+import org.jivesoftware.smack.packet.Bind;
+import org.jivesoftware.smack.packet.DefaultPacketExtension;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.Registration;
+import org.jivesoftware.smack.packet.RosterPacket;
+import org.jivesoftware.smack.packet.StreamError;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.provider.ProviderManager;
+import org.jivesoftware.smack.sasl.SASLMechanism.Failure;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+/**
+ * Utility class that helps to parse packets. Any parsing packets method that must be shared
+ * between many clients must be placed in this utility class.
+ *
+ * @author Gaston Dombiak
+ */
+public class PacketParserUtils {
+
+    /**
+     * Namespace used to store packet properties.
+     */
+    private static final String PROPERTIES_NAMESPACE =
+            "http://www.jivesoftware.com/xmlns/xmpp/properties";
+
+    /**
+     * Parses a message packet.
+     *
+     * @param parser the XML parser, positioned at the start of a message packet.
+     * @return a Message packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Packet parseMessage(XmlPullParser parser) throws Exception {
+        Message message = new Message();
+        String id = parser.getAttributeValue("", "id");
+        message.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+        message.setTo(parser.getAttributeValue("", "to"));
+        message.setFrom(parser.getAttributeValue("", "from"));
+        message.setType(Message.Type.fromString(parser.getAttributeValue("", "type")));
+        String language = getLanguageAttribute(parser);
+        
+        // determine message's default language
+        String defaultLanguage = null;
+        if (language != null && !"".equals(language.trim())) {
+            message.setLanguage(language);
+            defaultLanguage = language;
+        } 
+        else {
+            defaultLanguage = Packet.getDefaultLanguage();
+        }
+
+        // Parse sub-elements. We include extra logic to make sure the values
+        // are only read once. This is because it's possible for the names to appear
+        // in arbitrary sub-elements.
+        boolean done = false;
+        String thread = null;
+        Map<String, Object> properties = null;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("subject")) {
+                    String xmlLang = getLanguageAttribute(parser);
+                    if (xmlLang == null) {
+                        xmlLang = defaultLanguage;
+                    }
+
+                    String subject = parseContent(parser);
+
+                    if (message.getSubject(xmlLang) == null) {
+                        message.addSubject(xmlLang, subject);
+                    }
+                }
+                else if (elementName.equals("body")) {
+                    String xmlLang = getLanguageAttribute(parser);
+                    if (xmlLang == null) {
+                        xmlLang = defaultLanguage;
+                    }
+
+                    String body = parseContent(parser);
+                    
+                    if (message.getBody(xmlLang) == null) {
+                        message.addBody(xmlLang, body);
+                    }
+                }
+                else if (elementName.equals("thread")) {
+                    if (thread == null) {
+                        thread = parser.nextText();
+                    }
+                }
+                else if (elementName.equals("error")) {
+                    message.setError(parseError(parser));
+                }
+                else if (elementName.equals("properties") &&
+                        namespace.equals(PROPERTIES_NAMESPACE))
+                {
+                    properties = parseProperties(parser);
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    message.addExtension(
+                    PacketParserUtils.parsePacketExtension(elementName, namespace, parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("message")) {
+                    done = true;
+                }
+            }
+        }
+
+        message.setThread(thread);
+        // Set packet properties.
+        if (properties != null) {
+            for (String name : properties.keySet()) {
+                message.setProperty(name, properties.get(name));
+            }
+        }
+        return message;
+    }
+
+    /**
+     * Returns the content of a tag as string regardless of any tags included.
+     * 
+     * @param parser the XML pull parser
+     * @return the content of a tag as string
+     * @throws XmlPullParserException if parser encounters invalid XML
+     * @throws IOException if an IO error occurs
+     */
+    private static String parseContent(XmlPullParser parser)
+                    throws XmlPullParserException, IOException {
+        StringBuffer content = new StringBuffer();
+        int parserDepth = parser.getDepth();
+        while (!(parser.next() == XmlPullParser.END_TAG && parser
+                        .getDepth() == parserDepth)) {
+            content.append(parser.getText());
+        }
+        return content.toString();
+    }
+
+    /**
+     * Parses a presence packet.
+     *
+     * @param parser the XML parser, positioned at the start of a presence packet.
+     * @return a Presence packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Presence parsePresence(XmlPullParser parser) throws Exception {
+        Presence.Type type = Presence.Type.available;
+        String typeString = parser.getAttributeValue("", "type");
+        if (typeString != null && !typeString.equals("")) {
+            try {
+                type = Presence.Type.valueOf(typeString);
+            }
+            catch (IllegalArgumentException iae) {
+                System.err.println("Found invalid presence type " + typeString);
+            }
+        }
+        Presence presence = new Presence(type);
+        presence.setTo(parser.getAttributeValue("", "to"));
+        presence.setFrom(parser.getAttributeValue("", "from"));
+        String id = parser.getAttributeValue("", "id");
+        presence.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+
+        String language = getLanguageAttribute(parser);
+        if (language != null && !"".equals(language.trim())) {
+        	presence.setLanguage(language);
+        }
+        presence.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+
+        // Parse sub-elements
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("status")) {
+                    presence.setStatus(parser.nextText());
+                }
+                else if (elementName.equals("priority")) {
+                    try {
+                        int priority = Integer.parseInt(parser.nextText());
+                        presence.setPriority(priority);
+                    }
+                    catch (NumberFormatException nfe) {
+                        // Ignore.
+                    }
+                    catch (IllegalArgumentException iae) {
+                        // Presence priority is out of range so assume priority to be zero
+                        presence.setPriority(0);
+                    }
+                }
+                else if (elementName.equals("show")) {
+                    String modeText = parser.nextText();
+                    try {
+                        presence.setMode(Presence.Mode.valueOf(modeText));
+                    }
+                    catch (IllegalArgumentException iae) {
+                        System.err.println("Found invalid presence mode " + modeText);
+                    }
+                }
+                else if (elementName.equals("error")) {
+                    presence.setError(parseError(parser));
+                }
+                else if (elementName.equals("properties") &&
+                        namespace.equals(PROPERTIES_NAMESPACE))
+                {
+                    Map<String,Object> properties = parseProperties(parser);
+                    // Set packet properties.
+                    for (String name : properties.keySet()) {
+                        presence.setProperty(name, properties.get(name));
+                    }
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                	try {
+                        presence.addExtension(PacketParserUtils.parsePacketExtension(elementName, namespace, parser));
+                	}
+                	catch (Exception e) {
+                		System.err.println("Failed to parse extension packet in Presence packet.");
+                	}
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("presence")) {
+                    done = true;
+                }
+            }
+        }
+        return presence;
+    }
+
+    /**
+     * Parses an IQ packet.
+     *
+     * @param parser the XML parser, positioned at the start of an IQ packet.
+     * @return an IQ object.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static IQ parseIQ(XmlPullParser parser, Connection connection) throws Exception {
+        IQ iqPacket = null;
+
+        String id = parser.getAttributeValue("", "id");
+        String to = parser.getAttributeValue("", "to");
+        String from = parser.getAttributeValue("", "from");
+        IQ.Type type = IQ.Type.fromString(parser.getAttributeValue("", "type"));
+        XMPPError error = null;
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("error")) {
+                    error = PacketParserUtils.parseError(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:auth")) {
+                    iqPacket = parseAuthentication(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:roster")) {
+                    iqPacket = parseRoster(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:register")) {
+                    iqPacket = parseRegistration(parser);
+                }
+                else if (elementName.equals("bind") &&
+                        namespace.equals("urn:ietf:params:xml:ns:xmpp-bind")) {
+                    iqPacket = parseResourceBinding(parser);
+                }
+                // Otherwise, see if there is a registered provider for
+                // this element name and namespace.
+                else {
+                    Object provider = ProviderManager.getInstance().getIQProvider(elementName, namespace);
+                    if (provider != null) {
+                        if (provider instanceof IQProvider) {
+                            iqPacket = ((IQProvider)provider).parseIQ(parser);
+                        }
+                        else if (provider instanceof Class) {
+                            iqPacket = (IQ)PacketParserUtils.parseWithIntrospection(elementName,
+                                    (Class<?>)provider, parser);
+                        }
+                    }
+                    // Only handle unknown IQs of type result. Types of 'get' and 'set' which are not understood
+                    // have to be answered with an IQ error response. See the code a few lines below
+                    else if (IQ.Type.RESULT == type){
+                        // No Provider found for the IQ stanza, parse it to an UnparsedIQ instance
+                        // so that the content of the IQ can be examined later on
+                        iqPacket = new UnparsedResultIQ(parseContent(parser));
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("iq")) {
+                    done = true;
+                }
+            }
+        }
+        // Decide what to do when an IQ packet was not understood
+        if (iqPacket == null) {
+            if (IQ.Type.GET == type || IQ.Type.SET == type ) {
+                // If the IQ stanza is of type "get" or "set" containing a child element
+                // qualified by a namespace it does not understand, then answer an IQ of
+                // type "error" with code 501 ("feature-not-implemented")
+                iqPacket = new IQ() {
+                    @Override
+                    public String getChildElementXML() {
+                        return null;
+                    }
+                };
+                iqPacket.setPacketID(id);
+                iqPacket.setTo(from);
+                iqPacket.setFrom(to);
+                iqPacket.setType(IQ.Type.ERROR);
+                iqPacket.setError(new XMPPError(XMPPError.Condition.feature_not_implemented));
+                connection.sendPacket(iqPacket);
+                return null;
+            }
+            else {
+                // If an IQ packet wasn't created above, create an empty IQ packet.
+                iqPacket = new IQ() {
+                    @Override
+                    public String getChildElementXML() {
+                        return null;
+                    }
+                };
+            }
+        }
+
+        // Set basic values on the iq packet.
+        iqPacket.setPacketID(id);
+        iqPacket.setTo(to);
+        iqPacket.setFrom(from);
+        iqPacket.setType(type);
+        iqPacket.setError(error);
+
+        return iqPacket;
+    }
+
+    private static Authentication parseAuthentication(XmlPullParser parser) throws Exception {
+        Authentication authentication = new Authentication();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("username")) {
+                    authentication.setUsername(parser.nextText());
+                }
+                else if (parser.getName().equals("password")) {
+                    authentication.setPassword(parser.nextText());
+                }
+                else if (parser.getName().equals("digest")) {
+                    authentication.setDigest(parser.nextText());
+                }
+                else if (parser.getName().equals("resource")) {
+                    authentication.setResource(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        return authentication;
+    }
+
+    private static RosterPacket parseRoster(XmlPullParser parser) throws Exception {
+        RosterPacket roster = new RosterPacket();
+        boolean done = false;
+        RosterPacket.Item item = null;
+        while (!done) {
+        	if(parser.getEventType()==XmlPullParser.START_TAG && 
+        			parser.getName().equals("query")){
+        		String version = parser.getAttributeValue(null, "ver");
+        		roster.setVersion(version);
+        	}
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                    String jid = parser.getAttributeValue("", "jid");
+                    String name = parser.getAttributeValue("", "name");
+                    // Create packet.
+                    item = new RosterPacket.Item(jid, name);
+                    // Set status.
+                    String ask = parser.getAttributeValue("", "ask");
+                    RosterPacket.ItemStatus status = RosterPacket.ItemStatus.fromString(ask);
+                    item.setItemStatus(status);
+                    // Set type.
+                    String subscription = parser.getAttributeValue("", "subscription");
+                    RosterPacket.ItemType type = RosterPacket.ItemType.valueOf(subscription != null ? subscription : "none");
+                    item.setItemType(type);
+                }
+                if (parser.getName().equals("group") && item!= null) {
+                    final String groupName = parser.nextText();
+                    if (groupName != null && groupName.trim().length() > 0) {
+                        item.addGroupName(groupName);
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    roster.addRosterItem(item);
+                }
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        return roster;
+    }
+
+     private static Registration parseRegistration(XmlPullParser parser) throws Exception {
+        Registration registration = new Registration();
+        Map<String, String> fields = null;
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                // Any element that's in the jabber:iq:register namespace,
+                // attempt to parse it if it's in the form <name>value</name>.
+                if (parser.getNamespace().equals("jabber:iq:register")) {
+                    String name = parser.getName();
+                    String value = "";
+                    if (fields == null) {
+                        fields = new HashMap<String, String>();
+                    }
+
+                    if (parser.next() == XmlPullParser.TEXT) {
+                        value = parser.getText();
+                    }
+                    // Ignore instructions, but anything else should be added to the map.
+                    if (!name.equals("instructions")) {
+                        fields.put(name, value);
+                    }
+                    else {
+                        registration.setInstructions(value);
+                    }
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    registration.addExtension(
+                        PacketParserUtils.parsePacketExtension(
+                            parser.getName(),
+                            parser.getNamespace(),
+                            parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        registration.setAttributes(fields);
+        return registration;
+    }
+
+    private static Bind parseResourceBinding(XmlPullParser parser) throws IOException,
+            XmlPullParserException {
+        Bind bind = new Bind();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("resource")) {
+                    bind.setResource(parser.nextText());
+                }
+                else if (parser.getName().equals("jid")) {
+                    bind.setJid(parser.nextText());
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("bind")) {
+                    done = true;
+                }
+            }
+        }
+
+        return bind;
+    }
+
+    /**
+     * Parse the available SASL mechanisms reported from the server.
+     *
+     * @param parser the XML parser, positioned at the start of the mechanisms stanza.
+     * @return a collection of Stings with the mechanisms included in the mechanisms stanza.
+     * @throws Exception if an exception occurs while parsing the stanza.
+     */
+    public static Collection<String> parseMechanisms(XmlPullParser parser) throws Exception {
+        List<String> mechanisms = new ArrayList<String>();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                if (elementName.equals("mechanism")) {
+                    mechanisms.add(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("mechanisms")) {
+                    done = true;
+                }
+            }
+        }
+        return mechanisms;
+    }
+
+    /**
+     * Parse the available compression methods reported from the server.
+     *
+     * @param parser the XML parser, positioned at the start of the compression stanza.
+     * @return a collection of Stings with the methods included in the compression stanza.
+     * @throws Exception if an exception occurs while parsing the stanza.
+     */
+    public static Collection<String> parseCompressionMethods(XmlPullParser parser)
+            throws IOException, XmlPullParserException {
+        List<String> methods = new ArrayList<String>();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                if (elementName.equals("method")) {
+                    methods.add(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("compression")) {
+                    done = true;
+                }
+            }
+        }
+        return methods;
+    }
+
+    /**
+     * Parse a properties sub-packet. If any errors occur while de-serializing Java object
+     * properties, an exception will be printed and not thrown since a thrown
+     * exception will shut down the entire connection. ClassCastExceptions will occur
+     * when both the sender and receiver of the packet don't have identical versions
+     * of the same class.
+     *
+     * @param parser the XML parser, positioned at the start of a properties sub-packet.
+     * @return a map of the properties.
+     * @throws Exception if an error occurs while parsing the properties.
+     */
+    public static Map<String, Object> parseProperties(XmlPullParser parser) throws Exception {
+        Map<String, Object> properties = new HashMap<String, Object>();
+        while (true) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG && parser.getName().equals("property")) {
+                // Parse a property
+                boolean done = false;
+                String name = null;
+                String type = null;
+                String valueText = null;
+                Object value = null;
+                while (!done) {
+                    eventType = parser.next();
+                    if (eventType == XmlPullParser.START_TAG) {
+                        String elementName = parser.getName();
+                        if (elementName.equals("name")) {
+                            name = parser.nextText();
+                        }
+                        else if (elementName.equals("value")) {
+                            type = parser.getAttributeValue("", "type");
+                            valueText = parser.nextText();
+                        }
+                    }
+                    else if (eventType == XmlPullParser.END_TAG) {
+                        if (parser.getName().equals("property")) {
+                            if ("integer".equals(type)) {
+                                value = Integer.valueOf(valueText);
+                            }
+                            else if ("long".equals(type))  {
+                                value = Long.valueOf(valueText);
+                            }
+                            else if ("float".equals(type)) {
+                                value = Float.valueOf(valueText);
+                            }
+                            else if ("double".equals(type)) {
+                                value = Double.valueOf(valueText);
+                            }
+                            else if ("boolean".equals(type)) {
+                                value = Boolean.valueOf(valueText);
+                            }
+                            else if ("string".equals(type)) {
+                                value = valueText;
+                            }
+                            else if ("java-object".equals(type)) {
+                                try {
+                                    byte [] bytes = StringUtils.decodeBase64(valueText);
+                                    ObjectInputStream in = new ObjectInputStream(new ByteArrayInputStream(bytes));
+                                    value = in.readObject();
+                                }
+                                catch (Exception e) {
+                                    e.printStackTrace();
+                                }
+                            }
+                            if (name != null && value != null) {
+                                properties.put(name, value);
+                            }
+                            done = true;
+                        }
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("properties")) {
+                    break;
+                }
+            }
+        }
+        return properties;
+    }
+
+    /**
+     * Parses SASL authentication error packets.
+     * 
+     * @param parser the XML parser.
+     * @return a SASL Failure packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Failure parseSASLFailure(XmlPullParser parser) throws Exception {
+        String condition = null;
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                if (!parser.getName().equals("failure")) {
+                    condition = parser.getName();
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("failure")) {
+                    done = true;
+                }
+            }
+        }
+        return new Failure(condition);
+    }
+
+    /**
+     * Parses stream error packets.
+     *
+     * @param parser the XML parser.
+     * @return an stream error packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static StreamError parseStreamError(XmlPullParser parser) throws IOException,
+            XmlPullParserException {
+    StreamError streamError = null;
+    boolean done = false;
+    while (!done) {
+        int eventType = parser.next();
+
+        if (eventType == XmlPullParser.START_TAG) {
+            streamError = new StreamError(parser.getName());
+        }
+        else if (eventType == XmlPullParser.END_TAG) {
+            if (parser.getName().equals("error")) {
+                done = true;
+            }
+        }
+    }
+    return streamError;
+}
+
+    /**
+     * Parses error sub-packets.
+     *
+     * @param parser the XML parser.
+     * @return an error sub-packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static XMPPError parseError(XmlPullParser parser) throws Exception {
+        final String errorNamespace = "urn:ietf:params:xml:ns:xmpp-stanzas";
+    	String errorCode = "-1";
+        String type = null;
+        String message = null;
+        String condition = null;
+        List<PacketExtension> extensions = new ArrayList<PacketExtension>();
+
+        // Parse the error header
+        for (int i=0; i<parser.getAttributeCount(); i++) {
+            if (parser.getAttributeName(i).equals("code")) {
+                errorCode = parser.getAttributeValue("", "code");
+            }
+            if (parser.getAttributeName(i).equals("type")) {
+            	type = parser.getAttributeValue("", "type");
+            }
+        }
+        boolean done = false;
+        // Parse the text and condition tags
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("text")) {
+                    message = parser.nextText();
+                }
+                else {
+                	// Condition tag, it can be xmpp error or an application defined error.
+                    String elementName = parser.getName();
+                    String namespace = parser.getNamespace();
+                    if (errorNamespace.equals(namespace)) {
+                    	condition = elementName;
+                    }
+                    else {
+                    	extensions.add(parsePacketExtension(elementName, namespace, parser));
+                    }
+                }
+            }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("error")) {
+                        done = true;
+                    }
+                }
+        }
+        // Parse the error type.
+        XMPPError.Type errorType = XMPPError.Type.CANCEL;
+        try {
+            if (type != null) {
+                errorType = XMPPError.Type.valueOf(type.toUpperCase());
+            }
+        }
+        catch (IllegalArgumentException iae) {
+            // Print stack trace. We shouldn't be getting an illegal error type.
+            iae.printStackTrace();
+        }
+        return new XMPPError(Integer.parseInt(errorCode), errorType, condition, message, extensions);
+    }
+
+    /**
+     * Parses a packet extension sub-packet.
+     *
+     * @param elementName the XML element name of the packet extension.
+     * @param namespace the XML namespace of the packet extension.
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public static PacketExtension parsePacketExtension(String elementName, String namespace, XmlPullParser parser)
+            throws Exception
+    {
+        // See if a provider is registered to handle the extension.
+        Object provider = ProviderManager.getInstance().getExtensionProvider(elementName, namespace);
+        if (provider != null) {
+            if (provider instanceof PacketExtensionProvider) {
+                return ((PacketExtensionProvider)provider).parseExtension(parser);
+            }
+            else if (provider instanceof Class) {
+                return (PacketExtension)parseWithIntrospection(
+                        elementName, (Class<?>)provider, parser);
+            }
+        }
+        // No providers registered, so use a default extension.
+        DefaultPacketExtension extension = new DefaultPacketExtension(elementName, namespace);
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String name = parser.getName();
+                // If an empty element, set the value with the empty string.
+                if (parser.isEmptyElementTag()) {
+                    extension.setValue(name,"");
+                }
+                // Otherwise, get the the element text.
+                else {
+                    eventType = parser.next();
+                    if (eventType == XmlPullParser.TEXT) {
+                        String value = parser.getText();
+                        extension.setValue(name, value);
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(elementName)) {
+                    done = true;
+                }
+            }
+        }
+        return extension;
+    }
+
+    private static String getLanguageAttribute(XmlPullParser parser) {
+    	for (int i = 0; i < parser.getAttributeCount(); i++) {
+            String attributeName = parser.getAttributeName(i);
+            if ( "xml:lang".equals(attributeName) ||
+                    ("lang".equals(attributeName) &&
+                            "xml".equals(parser.getAttributePrefix(i)))) {
+    			return parser.getAttributeValue(i);
+    		}
+    	}
+    	return null;
+    }
+
+    public static Object parseWithIntrospection(String elementName,
+            Class<?> objectClass, XmlPullParser parser) throws Exception
+    {
+        boolean done = false;
+        Object object = objectClass.newInstance();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String name = parser.getName();
+                String stringValue = parser.nextText();
+                Class propertyType = object.getClass().getMethod(
+                    "get" + Character.toUpperCase(name.charAt(0)) + name.substring(1)).getReturnType();
+                // Get the value of the property by converting it from a
+                // String to the correct object type.
+                Object value = decode(propertyType, stringValue);
+                // Set the value of the bean.
+                object.getClass().getMethod("set" + Character.toUpperCase(name.charAt(0)) + name.substring(1), propertyType)
+                .invoke(object, value);
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(elementName)) {
+                    done = true;
+                }
+            }
+        }
+        return object;
+            }
+
+    /**
+     * Decodes a String into an object of the specified type. If the object
+     * type is not supported, null will be returned.
+     *
+     * @param type the type of the property.
+     * @param value the encode String value to decode.
+     * @return the String value decoded into the specified type.
+     * @throws Exception If decoding failed due to an error.
+     */
+    private static Object decode(Class<?> type, String value) throws Exception {
+        if (type.getName().equals("java.lang.String")) {
+            return value;
+        }
+        if (type.getName().equals("boolean")) {
+            return Boolean.valueOf(value);
+        }
+        if (type.getName().equals("int")) {
+            return Integer.valueOf(value);
+        }
+        if (type.getName().equals("long")) {
+            return Long.valueOf(value);
+        }
+        if (type.getName().equals("float")) {
+            return Float.valueOf(value);
+        }
+        if (type.getName().equals("double")) {
+            return Double.valueOf(value);
+        }
+        if (type.getName().equals("java.lang.Class")) {
+            return Class.forName(value);
+        }
+        return null;
+    }
+
+    /**
+     * This class represents and unparsed IQ of the type 'result'. Usually it's created when no IQProvider
+     * was found for the IQ element.
+     * 
+     * The child elements can be examined with the getChildElementXML() method.
+     *
+     */
+    public static class UnparsedResultIQ extends IQ {
+        public UnparsedResultIQ(String content) {
+            this.str = content;
+        }
+
+        private final String str;
+
+        @Override
+        public String getChildElementXML() {
+            return this.str;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/PacketParserUtils.java.orig b/src/org/jivesoftware/smack/util/PacketParserUtils.java.orig
new file mode 100644
index 0000000..1c518f6
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/PacketParserUtils.java.orig
@@ -0,0 +1,926 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.beans.PropertyDescriptor;
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.Authentication;
+import org.jivesoftware.smack.packet.Bind;
+import org.jivesoftware.smack.packet.DefaultPacketExtension;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.Registration;
+import org.jivesoftware.smack.packet.RosterPacket;
+import org.jivesoftware.smack.packet.StreamError;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.provider.ProviderManager;
+import org.jivesoftware.smack.sasl.SASLMechanism.Failure;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+/**
+ * Utility class that helps to parse packets. Any parsing packets method that must be shared
+ * between many clients must be placed in this utility class.
+ *
+ * @author Gaston Dombiak
+ */
+public class PacketParserUtils {
+
+    /**
+     * Namespace used to store packet properties.
+     */
+    private static final String PROPERTIES_NAMESPACE =
+            "http://www.jivesoftware.com/xmlns/xmpp/properties";
+
+    /**
+     * Parses a message packet.
+     *
+     * @param parser the XML parser, positioned at the start of a message packet.
+     * @return a Message packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Packet parseMessage(XmlPullParser parser) throws Exception {
+        Message message = new Message();
+        String id = parser.getAttributeValue("", "id");
+        message.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+        message.setTo(parser.getAttributeValue("", "to"));
+        message.setFrom(parser.getAttributeValue("", "from"));
+        message.setType(Message.Type.fromString(parser.getAttributeValue("", "type")));
+        String language = getLanguageAttribute(parser);
+        
+        // determine message's default language
+        String defaultLanguage = null;
+        if (language != null && !"".equals(language.trim())) {
+            message.setLanguage(language);
+            defaultLanguage = language;
+        } 
+        else {
+            defaultLanguage = Packet.getDefaultLanguage();
+        }
+
+        // Parse sub-elements. We include extra logic to make sure the values
+        // are only read once. This is because it's possible for the names to appear
+        // in arbitrary sub-elements.
+        boolean done = false;
+        String thread = null;
+        Map<String, Object> properties = null;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("subject")) {
+                    String xmlLang = getLanguageAttribute(parser);
+                    if (xmlLang == null) {
+                        xmlLang = defaultLanguage;
+                    }
+
+                    String subject = parseContent(parser);
+
+                    if (message.getSubject(xmlLang) == null) {
+                        message.addSubject(xmlLang, subject);
+                    }
+                }
+                else if (elementName.equals("body")) {
+                    String xmlLang = getLanguageAttribute(parser);
+                    if (xmlLang == null) {
+                        xmlLang = defaultLanguage;
+                    }
+
+                    String body = parseContent(parser);
+                    
+                    if (message.getBody(xmlLang) == null) {
+                        message.addBody(xmlLang, body);
+                    }
+                }
+                else if (elementName.equals("thread")) {
+                    if (thread == null) {
+                        thread = parser.nextText();
+                    }
+                }
+                else if (elementName.equals("error")) {
+                    message.setError(parseError(parser));
+                }
+                else if (elementName.equals("properties") &&
+                        namespace.equals(PROPERTIES_NAMESPACE))
+                {
+                    properties = parseProperties(parser);
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    message.addExtension(
+                    PacketParserUtils.parsePacketExtension(elementName, namespace, parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("message")) {
+                    done = true;
+                }
+            }
+        }
+
+        message.setThread(thread);
+        // Set packet properties.
+        if (properties != null) {
+            for (String name : properties.keySet()) {
+                message.setProperty(name, properties.get(name));
+            }
+        }
+        return message;
+    }
+
+    /**
+     * Returns the content of a tag as string regardless of any tags included.
+     * 
+     * @param parser the XML pull parser
+     * @return the content of a tag as string
+     * @throws XmlPullParserException if parser encounters invalid XML
+     * @throws IOException if an IO error occurs
+     */
+    private static String parseContent(XmlPullParser parser)
+                    throws XmlPullParserException, IOException {
+        StringBuffer content = new StringBuffer();
+        int parserDepth = parser.getDepth();
+        while (!(parser.next() == XmlPullParser.END_TAG && parser
+                        .getDepth() == parserDepth)) {
+            content.append(parser.getText());
+        }
+        return content.toString();
+    }
+
+    /**
+     * Parses a presence packet.
+     *
+     * @param parser the XML parser, positioned at the start of a presence packet.
+     * @return a Presence packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Presence parsePresence(XmlPullParser parser) throws Exception {
+        Presence.Type type = Presence.Type.available;
+        String typeString = parser.getAttributeValue("", "type");
+        if (typeString != null && !typeString.equals("")) {
+            try {
+                type = Presence.Type.valueOf(typeString);
+            }
+            catch (IllegalArgumentException iae) {
+                System.err.println("Found invalid presence type " + typeString);
+            }
+        }
+        Presence presence = new Presence(type);
+        presence.setTo(parser.getAttributeValue("", "to"));
+        presence.setFrom(parser.getAttributeValue("", "from"));
+        String id = parser.getAttributeValue("", "id");
+        presence.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+
+        String language = getLanguageAttribute(parser);
+        if (language != null && !"".equals(language.trim())) {
+        	presence.setLanguage(language);
+        }
+        presence.setPacketID(id == null ? Packet.ID_NOT_AVAILABLE : id);
+
+        // Parse sub-elements
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("status")) {
+                    presence.setStatus(parser.nextText());
+                }
+                else if (elementName.equals("priority")) {
+                    try {
+                        int priority = Integer.parseInt(parser.nextText());
+                        presence.setPriority(priority);
+                    }
+                    catch (NumberFormatException nfe) {
+                        // Ignore.
+                    }
+                    catch (IllegalArgumentException iae) {
+                        // Presence priority is out of range so assume priority to be zero
+                        presence.setPriority(0);
+                    }
+                }
+                else if (elementName.equals("show")) {
+                    String modeText = parser.nextText();
+                    try {
+                        presence.setMode(Presence.Mode.valueOf(modeText));
+                    }
+                    catch (IllegalArgumentException iae) {
+                        System.err.println("Found invalid presence mode " + modeText);
+                    }
+                }
+                else if (elementName.equals("error")) {
+                    presence.setError(parseError(parser));
+                }
+                else if (elementName.equals("properties") &&
+                        namespace.equals(PROPERTIES_NAMESPACE))
+                {
+                    Map<String,Object> properties = parseProperties(parser);
+                    // Set packet properties.
+                    for (String name : properties.keySet()) {
+                        presence.setProperty(name, properties.get(name));
+                    }
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                	try {
+                        presence.addExtension(PacketParserUtils.parsePacketExtension(elementName, namespace, parser));
+                	}
+                	catch (Exception e) {
+                		System.err.println("Failed to parse extension packet in Presence packet.");
+                	}
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("presence")) {
+                    done = true;
+                }
+            }
+        }
+        return presence;
+    }
+
+    /**
+     * Parses an IQ packet.
+     *
+     * @param parser the XML parser, positioned at the start of an IQ packet.
+     * @return an IQ object.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static IQ parseIQ(XmlPullParser parser, Connection connection) throws Exception {
+        IQ iqPacket = null;
+
+        String id = parser.getAttributeValue("", "id");
+        String to = parser.getAttributeValue("", "to");
+        String from = parser.getAttributeValue("", "from");
+        IQ.Type type = IQ.Type.fromString(parser.getAttributeValue("", "type"));
+        XMPPError error = null;
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                String namespace = parser.getNamespace();
+                if (elementName.equals("error")) {
+                    error = PacketParserUtils.parseError(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:auth")) {
+                    iqPacket = parseAuthentication(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:roster")) {
+                    iqPacket = parseRoster(parser);
+                }
+                else if (elementName.equals("query") && namespace.equals("jabber:iq:register")) {
+                    iqPacket = parseRegistration(parser);
+                }
+                else if (elementName.equals("bind") &&
+                        namespace.equals("urn:ietf:params:xml:ns:xmpp-bind")) {
+                    iqPacket = parseResourceBinding(parser);
+                }
+                // Otherwise, see if there is a registered provider for
+                // this element name and namespace.
+                else {
+                    Object provider = ProviderManager.getInstance().getIQProvider(elementName, namespace);
+                    if (provider != null) {
+                        if (provider instanceof IQProvider) {
+                            iqPacket = ((IQProvider)provider).parseIQ(parser);
+                        }
+                        else if (provider instanceof Class) {
+                            iqPacket = (IQ)PacketParserUtils.parseWithIntrospection(elementName,
+                                    (Class<?>)provider, parser);
+                        }
+                    }
+                    // Only handle unknown IQs of type result. Types of 'get' and 'set' which are not understood
+                    // have to be answered with an IQ error response. See the code a few lines below
+                    else if (IQ.Type.RESULT == type){
+                        // No Provider found for the IQ stanza, parse it to an UnparsedIQ instance
+                        // so that the content of the IQ can be examined later on
+                        iqPacket = new UnparsedResultIQ(parseContent(parser));
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("iq")) {
+                    done = true;
+                }
+            }
+        }
+        // Decide what to do when an IQ packet was not understood
+        if (iqPacket == null) {
+            if (IQ.Type.GET == type || IQ.Type.SET == type ) {
+                // If the IQ stanza is of type "get" or "set" containing a child element
+                // qualified by a namespace it does not understand, then answer an IQ of
+                // type "error" with code 501 ("feature-not-implemented")
+                iqPacket = new IQ() {
+                    @Override
+                    public String getChildElementXML() {
+                        return null;
+                    }
+                };
+                iqPacket.setPacketID(id);
+                iqPacket.setTo(from);
+                iqPacket.setFrom(to);
+                iqPacket.setType(IQ.Type.ERROR);
+                iqPacket.setError(new XMPPError(XMPPError.Condition.feature_not_implemented));
+                connection.sendPacket(iqPacket);
+                return null;
+            }
+            else {
+                // If an IQ packet wasn't created above, create an empty IQ packet.
+                iqPacket = new IQ() {
+                    @Override
+                    public String getChildElementXML() {
+                        return null;
+                    }
+                };
+            }
+        }
+
+        // Set basic values on the iq packet.
+        iqPacket.setPacketID(id);
+        iqPacket.setTo(to);
+        iqPacket.setFrom(from);
+        iqPacket.setType(type);
+        iqPacket.setError(error);
+
+        return iqPacket;
+    }
+
+    private static Authentication parseAuthentication(XmlPullParser parser) throws Exception {
+        Authentication authentication = new Authentication();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("username")) {
+                    authentication.setUsername(parser.nextText());
+                }
+                else if (parser.getName().equals("password")) {
+                    authentication.setPassword(parser.nextText());
+                }
+                else if (parser.getName().equals("digest")) {
+                    authentication.setDigest(parser.nextText());
+                }
+                else if (parser.getName().equals("resource")) {
+                    authentication.setResource(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        return authentication;
+    }
+
+    private static RosterPacket parseRoster(XmlPullParser parser) throws Exception {
+        RosterPacket roster = new RosterPacket();
+        boolean done = false;
+        RosterPacket.Item item = null;
+        while (!done) {
+        	if(parser.getEventType()==XmlPullParser.START_TAG && 
+        			parser.getName().equals("query")){
+        		String version = parser.getAttributeValue(null, "ver");
+        		roster.setVersion(version);
+        	}
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                    String jid = parser.getAttributeValue("", "jid");
+                    String name = parser.getAttributeValue("", "name");
+                    // Create packet.
+                    item = new RosterPacket.Item(jid, name);
+                    // Set status.
+                    String ask = parser.getAttributeValue("", "ask");
+                    RosterPacket.ItemStatus status = RosterPacket.ItemStatus.fromString(ask);
+                    item.setItemStatus(status);
+                    // Set type.
+                    String subscription = parser.getAttributeValue("", "subscription");
+                    RosterPacket.ItemType type = RosterPacket.ItemType.valueOf(subscription != null ? subscription : "none");
+                    item.setItemType(type);
+                }
+                if (parser.getName().equals("group") && item!= null) {
+                    final String groupName = parser.nextText();
+                    if (groupName != null && groupName.trim().length() > 0) {
+                        item.addGroupName(groupName);
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    roster.addRosterItem(item);
+                }
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        return roster;
+    }
+
+     private static Registration parseRegistration(XmlPullParser parser) throws Exception {
+        Registration registration = new Registration();
+        Map<String, String> fields = null;
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                // Any element that's in the jabber:iq:register namespace,
+                // attempt to parse it if it's in the form <name>value</name>.
+                if (parser.getNamespace().equals("jabber:iq:register")) {
+                    String name = parser.getName();
+                    String value = "";
+                    if (fields == null) {
+                        fields = new HashMap<String, String>();
+                    }
+
+                    if (parser.next() == XmlPullParser.TEXT) {
+                        value = parser.getText();
+                    }
+                    // Ignore instructions, but anything else should be added to the map.
+                    if (!name.equals("instructions")) {
+                        fields.put(name, value);
+                    }
+                    else {
+                        registration.setInstructions(value);
+                    }
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    registration.addExtension(
+                        PacketParserUtils.parsePacketExtension(
+                            parser.getName(),
+                            parser.getNamespace(),
+                            parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+        registration.setAttributes(fields);
+        return registration;
+    }
+
+    private static Bind parseResourceBinding(XmlPullParser parser) throws IOException,
+            XmlPullParserException {
+        Bind bind = new Bind();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("resource")) {
+                    bind.setResource(parser.nextText());
+                }
+                else if (parser.getName().equals("jid")) {
+                    bind.setJid(parser.nextText());
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("bind")) {
+                    done = true;
+                }
+            }
+        }
+
+        return bind;
+    }
+
+    /**
+     * Parse the available SASL mechanisms reported from the server.
+     *
+     * @param parser the XML parser, positioned at the start of the mechanisms stanza.
+     * @return a collection of Stings with the mechanisms included in the mechanisms stanza.
+     * @throws Exception if an exception occurs while parsing the stanza.
+     */
+    public static Collection<String> parseMechanisms(XmlPullParser parser) throws Exception {
+        List<String> mechanisms = new ArrayList<String>();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                if (elementName.equals("mechanism")) {
+                    mechanisms.add(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("mechanisms")) {
+                    done = true;
+                }
+            }
+        }
+        return mechanisms;
+    }
+
+    /**
+     * Parse the available compression methods reported from the server.
+     *
+     * @param parser the XML parser, positioned at the start of the compression stanza.
+     * @return a collection of Stings with the methods included in the compression stanza.
+     * @throws Exception if an exception occurs while parsing the stanza.
+     */
+    public static Collection<String> parseCompressionMethods(XmlPullParser parser)
+            throws IOException, XmlPullParserException {
+        List<String> methods = new ArrayList<String>();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elementName = parser.getName();
+                if (elementName.equals("method")) {
+                    methods.add(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("compression")) {
+                    done = true;
+                }
+            }
+        }
+        return methods;
+    }
+
+    /**
+     * Parse a properties sub-packet. If any errors occur while de-serializing Java object
+     * properties, an exception will be printed and not thrown since a thrown
+     * exception will shut down the entire connection. ClassCastExceptions will occur
+     * when both the sender and receiver of the packet don't have identical versions
+     * of the same class.
+     *
+     * @param parser the XML parser, positioned at the start of a properties sub-packet.
+     * @return a map of the properties.
+     * @throws Exception if an error occurs while parsing the properties.
+     */
+    public static Map<String, Object> parseProperties(XmlPullParser parser) throws Exception {
+        Map<String, Object> properties = new HashMap<String, Object>();
+        while (true) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG && parser.getName().equals("property")) {
+                // Parse a property
+                boolean done = false;
+                String name = null;
+                String type = null;
+                String valueText = null;
+                Object value = null;
+                while (!done) {
+                    eventType = parser.next();
+                    if (eventType == XmlPullParser.START_TAG) {
+                        String elementName = parser.getName();
+                        if (elementName.equals("name")) {
+                            name = parser.nextText();
+                        }
+                        else if (elementName.equals("value")) {
+                            type = parser.getAttributeValue("", "type");
+                            valueText = parser.nextText();
+                        }
+                    }
+                    else if (eventType == XmlPullParser.END_TAG) {
+                        if (parser.getName().equals("property")) {
+                            if ("integer".equals(type)) {
+                                value = Integer.valueOf(valueText);
+                            }
+                            else if ("long".equals(type))  {
+                                value = Long.valueOf(valueText);
+                            }
+                            else if ("float".equals(type)) {
+                                value = Float.valueOf(valueText);
+                            }
+                            else if ("double".equals(type)) {
+                                value = Double.valueOf(valueText);
+                            }
+                            else if ("boolean".equals(type)) {
+                                value = Boolean.valueOf(valueText);
+                            }
+                            else if ("string".equals(type)) {
+                                value = valueText;
+                            }
+                            else if ("java-object".equals(type)) {
+                                try {
+                                    byte [] bytes = StringUtils.decodeBase64(valueText);
+                                    ObjectInputStream in = new ObjectInputStream(new ByteArrayInputStream(bytes));
+                                    value = in.readObject();
+                                }
+                                catch (Exception e) {
+                                    e.printStackTrace();
+                                }
+                            }
+                            if (name != null && value != null) {
+                                properties.put(name, value);
+                            }
+                            done = true;
+                        }
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("properties")) {
+                    break;
+                }
+            }
+        }
+        return properties;
+    }
+
+    /**
+     * Parses SASL authentication error packets.
+     * 
+     * @param parser the XML parser.
+     * @return a SASL Failure packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static Failure parseSASLFailure(XmlPullParser parser) throws Exception {
+        String condition = null;
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                if (!parser.getName().equals("failure")) {
+                    condition = parser.getName();
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("failure")) {
+                    done = true;
+                }
+            }
+        }
+        return new Failure(condition);
+    }
+
+    /**
+     * Parses stream error packets.
+     *
+     * @param parser the XML parser.
+     * @return an stream error packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static StreamError parseStreamError(XmlPullParser parser) throws IOException,
+            XmlPullParserException {
+    StreamError streamError = null;
+    boolean done = false;
+    while (!done) {
+        int eventType = parser.next();
+
+        if (eventType == XmlPullParser.START_TAG) {
+            streamError = new StreamError(parser.getName());
+        }
+        else if (eventType == XmlPullParser.END_TAG) {
+            if (parser.getName().equals("error")) {
+                done = true;
+            }
+        }
+    }
+    return streamError;
+}
+
+    /**
+     * Parses error sub-packets.
+     *
+     * @param parser the XML parser.
+     * @return an error sub-packet.
+     * @throws Exception if an exception occurs while parsing the packet.
+     */
+    public static XMPPError parseError(XmlPullParser parser) throws Exception {
+        final String errorNamespace = "urn:ietf:params:xml:ns:xmpp-stanzas";
+    	String errorCode = "-1";
+        String type = null;
+        String message = null;
+        String condition = null;
+        List<PacketExtension> extensions = new ArrayList<PacketExtension>();
+
+        // Parse the error header
+        for (int i=0; i<parser.getAttributeCount(); i++) {
+            if (parser.getAttributeName(i).equals("code")) {
+                errorCode = parser.getAttributeValue("", "code");
+            }
+            if (parser.getAttributeName(i).equals("type")) {
+            	type = parser.getAttributeValue("", "type");
+            }
+        }
+        boolean done = false;
+        // Parse the text and condition tags
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("text")) {
+                    message = parser.nextText();
+                }
+                else {
+                	// Condition tag, it can be xmpp error or an application defined error.
+                    String elementName = parser.getName();
+                    String namespace = parser.getNamespace();
+                    if (errorNamespace.equals(namespace)) {
+                    	condition = elementName;
+                    }
+                    else {
+                    	extensions.add(parsePacketExtension(elementName, namespace, parser));
+                    }
+                }
+            }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("error")) {
+                        done = true;
+                    }
+                }
+        }
+        // Parse the error type.
+        XMPPError.Type errorType = XMPPError.Type.CANCEL;
+        try {
+            if (type != null) {
+                errorType = XMPPError.Type.valueOf(type.toUpperCase());
+            }
+        }
+        catch (IllegalArgumentException iae) {
+            // Print stack trace. We shouldn't be getting an illegal error type.
+            iae.printStackTrace();
+        }
+        return new XMPPError(Integer.parseInt(errorCode), errorType, condition, message, extensions);
+    }
+
+    /**
+     * Parses a packet extension sub-packet.
+     *
+     * @param elementName the XML element name of the packet extension.
+     * @param namespace the XML namespace of the packet extension.
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public static PacketExtension parsePacketExtension(String elementName, String namespace, XmlPullParser parser)
+            throws Exception
+    {
+        // See if a provider is registered to handle the extension.
+        Object provider = ProviderManager.getInstance().getExtensionProvider(elementName, namespace);
+        if (provider != null) {
+            if (provider instanceof PacketExtensionProvider) {
+                return ((PacketExtensionProvider)provider).parseExtension(parser);
+            }
+            else if (provider instanceof Class) {
+                return (PacketExtension)parseWithIntrospection(
+                        elementName, (Class<?>)provider, parser);
+            }
+        }
+        // No providers registered, so use a default extension.
+        DefaultPacketExtension extension = new DefaultPacketExtension(elementName, namespace);
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String name = parser.getName();
+                // If an empty element, set the value with the empty string.
+                if (parser.isEmptyElementTag()) {
+                    extension.setValue(name,"");
+                }
+                // Otherwise, get the the element text.
+                else {
+                    eventType = parser.next();
+                    if (eventType == XmlPullParser.TEXT) {
+                        String value = parser.getText();
+                        extension.setValue(name, value);
+                    }
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(elementName)) {
+                    done = true;
+                }
+            }
+        }
+        return extension;
+    }
+
+    private static String getLanguageAttribute(XmlPullParser parser) {
+    	for (int i = 0; i < parser.getAttributeCount(); i++) {
+            String attributeName = parser.getAttributeName(i);
+            if ( "xml:lang".equals(attributeName) ||
+                    ("lang".equals(attributeName) &&
+                            "xml".equals(parser.getAttributePrefix(i)))) {
+    			return parser.getAttributeValue(i);
+    		}
+    	}
+    	return null;
+    }
+
+    public static Object parseWithIntrospection(String elementName,
+            Class<?> objectClass, XmlPullParser parser) throws Exception
+    {
+        boolean done = false;
+        Object object = objectClass.newInstance();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                String name = parser.getName();
+                String stringValue = parser.nextText();
+                PropertyDescriptor descriptor = new PropertyDescriptor(name, objectClass);
+                // Load the class type of the property.
+                Class<?> propertyType = descriptor.getPropertyType();
+                // Get the value of the property by converting it from a
+                // String to the correct object type.
+                Object value = decode(propertyType, stringValue);
+                // Set the value of the bean.
+                descriptor.getWriteMethod().invoke(object, value);
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(elementName)) {
+                    done = true;
+                }
+            }
+        }
+        return object;
+            }
+
+    /**
+     * Decodes a String into an object of the specified type. If the object
+     * type is not supported, null will be returned.
+     *
+     * @param type the type of the property.
+     * @param value the encode String value to decode.
+     * @return the String value decoded into the specified type.
+     * @throws Exception If decoding failed due to an error.
+     */
+    private static Object decode(Class<?> type, String value) throws Exception {
+        if (type.getName().equals("java.lang.String")) {
+            return value;
+        }
+        if (type.getName().equals("boolean")) {
+            return Boolean.valueOf(value);
+        }
+        if (type.getName().equals("int")) {
+            return Integer.valueOf(value);
+        }
+        if (type.getName().equals("long")) {
+            return Long.valueOf(value);
+        }
+        if (type.getName().equals("float")) {
+            return Float.valueOf(value);
+        }
+        if (type.getName().equals("double")) {
+            return Double.valueOf(value);
+        }
+        if (type.getName().equals("java.lang.Class")) {
+            return Class.forName(value);
+        }
+        return null;
+    }
+
+    /**
+     * This class represents and unparsed IQ of the type 'result'. Usually it's created when no IQProvider
+     * was found for the IQ element.
+     * 
+     * The child elements can be examined with the getChildElementXML() method.
+     *
+     */
+    public static class UnparsedResultIQ extends IQ {
+        public UnparsedResultIQ(String content) {
+            this.str = content;
+        }
+
+        private final String str;
+
+        @Override
+        public String getChildElementXML() {
+            return this.str;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/ReaderListener.java b/src/org/jivesoftware/smack/util/ReaderListener.java
new file mode 100644
index 0000000..9f1f5bb
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/ReaderListener.java
@@ -0,0 +1,41 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+/**
+ * Interface that allows for implementing classes to listen for string reading
+ * events. Listeners are registered with ObservableReader objects.
+ *
+ * @see ObservableReader#addReaderListener
+ * @see ObservableReader#removeReaderListener
+ * 
+ * @author Gaston Dombiak
+ */
+public interface ReaderListener {
+
+    /**
+     * Notification that the Reader has read a new string.
+     * 
+     * @param str the read String
+     */
+    public abstract void read(String str);
+    
+}
diff --git a/src/org/jivesoftware/smack/util/StringEncoder.java b/src/org/jivesoftware/smack/util/StringEncoder.java
new file mode 100644
index 0000000..4c3d373
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/StringEncoder.java
@@ -0,0 +1,36 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * @author Florian Schmaus
+ */
+package org.jivesoftware.smack.util;
+
+public interface StringEncoder {
+    /**
+     * Encodes an string to another representation
+     * 
+     * @param string
+     * @return
+     */
+    String encode(String string);
+    
+    /**
+     * Decodes an string back to it's initial representation
+     * 
+     * @param string
+     * @return
+     */
+    String decode(String string);
+}
diff --git a/src/org/jivesoftware/smack/util/StringUtils.java b/src/org/jivesoftware/smack/util/StringUtils.java
new file mode 100644
index 0000000..7e3cfdc
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/StringUtils.java
@@ -0,0 +1,800 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+import java.io.UnsupportedEncodingException;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.text.DateFormat;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Calendar;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.Date;
+import java.util.List;
+import java.util.Random;
+import java.util.TimeZone;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * A collection of utility methods for String objects.
+ */
+public class StringUtils {
+
+	/**
+     * Date format as defined in XEP-0082 - XMPP Date and Time Profiles. The time zone is set to
+     * UTC.
+     * <p>
+     * Date formats are not synchronized. Since multiple threads access the format concurrently, it
+     * must be synchronized externally or you can use the convenience methods
+     * {@link #parseXEP0082Date(String)} and {@link #formatXEP0082Date(Date)}.
+     * @deprecated This public version will be removed in favor of using the methods defined within this class.
+     */
+    public static final DateFormat XEP_0082_UTC_FORMAT = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
+    
+    /*
+     * private version to use internally so we don't have to be concerned with thread safety.
+     */
+    private static final DateFormat dateFormatter = DateFormatType.XEP_0082_DATE_PROFILE.createFormatter();
+    private static final Pattern datePattern = Pattern.compile("^\\d+-\\d+-\\d+$");
+    
+    private static final DateFormat timeFormatter = DateFormatType.XEP_0082_TIME_MILLIS_ZONE_PROFILE.createFormatter();
+    private static final Pattern timePattern = Pattern.compile("^(\\d+:){2}\\d+.\\d+(Z|([+-](\\d+:\\d+)))$");
+    private static final DateFormat timeNoZoneFormatter = DateFormatType.XEP_0082_TIME_MILLIS_PROFILE.createFormatter();
+    private static final Pattern timeNoZonePattern = Pattern.compile("^(\\d+:){2}\\d+.\\d+$");
+    
+    private static final DateFormat timeNoMillisFormatter = DateFormatType.XEP_0082_TIME_ZONE_PROFILE.createFormatter();
+    private static final Pattern timeNoMillisPattern = Pattern.compile("^(\\d+:){2}\\d+(Z|([+-](\\d+:\\d+)))$");
+    private static final DateFormat timeNoMillisNoZoneFormatter = DateFormatType.XEP_0082_TIME_PROFILE.createFormatter();
+    private static final Pattern timeNoMillisNoZonePattern = Pattern.compile("^(\\d+:){2}\\d+$");
+    
+    private static final DateFormat dateTimeFormatter = DateFormatType.XEP_0082_DATETIME_MILLIS_PROFILE.createFormatter();
+    private static final Pattern dateTimePattern = Pattern.compile("^\\d+(-\\d+){2}+T(\\d+:){2}\\d+.\\d+(Z|([+-](\\d+:\\d+)))?$");
+    private static final DateFormat dateTimeNoMillisFormatter = DateFormatType.XEP_0082_DATETIME_PROFILE.createFormatter();
+    private static final Pattern dateTimeNoMillisPattern = Pattern.compile("^\\d+(-\\d+){2}+T(\\d+:){2}\\d+(Z|([+-](\\d+:\\d+)))?$");
+
+    private static final DateFormat xep0091Formatter = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+    private static final DateFormat xep0091Date6DigitFormatter = new SimpleDateFormat("yyyyMd'T'HH:mm:ss");
+    private static final DateFormat xep0091Date7Digit1MonthFormatter = new SimpleDateFormat("yyyyMdd'T'HH:mm:ss");
+    private static final DateFormat xep0091Date7Digit2MonthFormatter = new SimpleDateFormat("yyyyMMd'T'HH:mm:ss");
+    private static final Pattern xep0091Pattern = Pattern.compile("^\\d+T\\d+:\\d+:\\d+$");
+    
+    private static final List<PatternCouplings> couplings = new ArrayList<PatternCouplings>();
+    
+    static {
+    	TimeZone utc = TimeZone.getTimeZone("UTC");
+        XEP_0082_UTC_FORMAT.setTimeZone(utc);
+        dateFormatter.setTimeZone(utc);
+        timeFormatter.setTimeZone(utc);
+        timeNoZoneFormatter.setTimeZone(utc);
+        timeNoMillisFormatter.setTimeZone(utc);
+        timeNoMillisNoZoneFormatter.setTimeZone(utc);
+        dateTimeFormatter.setTimeZone(utc);
+        dateTimeNoMillisFormatter.setTimeZone(utc);
+        
+        xep0091Formatter.setTimeZone(utc);
+        xep0091Date6DigitFormatter.setTimeZone(utc);
+        xep0091Date7Digit1MonthFormatter.setTimeZone(utc);
+        xep0091Date7Digit1MonthFormatter.setLenient(false);
+        xep0091Date7Digit2MonthFormatter.setTimeZone(utc);
+        xep0091Date7Digit2MonthFormatter.setLenient(false);
+        
+        couplings.add(new PatternCouplings(datePattern, dateFormatter));
+        couplings.add(new PatternCouplings(dateTimePattern, dateTimeFormatter, true));
+        couplings.add(new PatternCouplings(dateTimeNoMillisPattern, dateTimeNoMillisFormatter, true));
+        couplings.add(new PatternCouplings(timePattern, timeFormatter, true));
+        couplings.add(new PatternCouplings(timeNoZonePattern, timeNoZoneFormatter));
+        couplings.add(new PatternCouplings(timeNoMillisPattern, timeNoMillisFormatter, true));
+        couplings.add(new PatternCouplings(timeNoMillisNoZonePattern, timeNoMillisNoZoneFormatter));
+    }
+
+    private static final char[] QUOTE_ENCODE = "&quot;".toCharArray();
+    private static final char[] APOS_ENCODE = "&apos;".toCharArray();
+    private static final char[] AMP_ENCODE = "&amp;".toCharArray();
+    private static final char[] LT_ENCODE = "&lt;".toCharArray();
+    private static final char[] GT_ENCODE = "&gt;".toCharArray();
+
+    /**
+     * Parses the given date string in the <a href="http://xmpp.org/extensions/xep-0082.html">XEP-0082 - XMPP Date and Time Profiles</a>.
+     * 
+     * @param dateString the date string to parse
+     * @return the parsed Date
+     * @throws ParseException if the specified string cannot be parsed
+     * @deprecated Use {@link #parseDate(String)} instead.
+     * 
+     */
+    public static Date parseXEP0082Date(String dateString) throws ParseException {
+    	return parseDate(dateString);
+    }
+    
+    /**
+     * Parses the given date string in either of the three profiles of <a href="http://xmpp.org/extensions/xep-0082.html">XEP-0082 - XMPP Date and Time Profiles</a>
+     * or <a href="http://xmpp.org/extensions/xep-0091.html">XEP-0091 - Legacy Delayed Delivery</a> format.
+     * <p>
+     * This method uses internal date formatters and is thus threadsafe.
+     * @param dateString the date string to parse
+     * @return the parsed Date
+     * @throws ParseException if the specified string cannot be parsed
+     */
+    public static Date parseDate(String dateString) throws ParseException {
+        Matcher matcher = xep0091Pattern.matcher(dateString);
+        
+        /*
+         * if date is in XEP-0091 format handle ambiguous dates missing the
+         * leading zero in month and day
+         */
+        if (matcher.matches()) {
+        	int length = dateString.split("T")[0].length();
+        	
+            if (length < 8) {
+                Date date = handleDateWithMissingLeadingZeros(dateString, length);
+
+                if (date != null)
+                	return date;
+            }
+            else {
+            	synchronized (xep0091Formatter) {
+                	return xep0091Formatter.parse(dateString);
+				}
+            }
+        }
+        else {
+        	for (PatternCouplings coupling : couplings) {
+                matcher = coupling.pattern.matcher(dateString);
+                
+                if (matcher.matches())
+                {
+                	if (coupling.needToConvertTimeZone) {
+                		dateString = coupling.convertTime(dateString);
+                	}
+                		
+                    synchronized (coupling.formatter) {
+                    	return coupling.formatter.parse(dateString);
+                    }
+                }
+			}
+        }
+        
+        /*
+         * We assume it is the XEP-0082 DateTime profile with no milliseconds at this point.  If it isn't, is is just not parseable, then we attempt
+         * to parse it regardless and let it throw the ParseException. 
+         */
+        synchronized (dateTimeNoMillisFormatter) {
+        	return dateTimeNoMillisFormatter.parse(dateString);
+        }
+    }
+    
+    /**
+     * Parses the given date string in different ways and returns the date that
+     * lies in the past and/or is nearest to the current date-time.
+     * 
+     * @param stampString date in string representation
+     * @param dateLength 
+     * @param noFuture 
+     * @return the parsed date
+     * @throws ParseException The date string was of an unknown format
+     */
+    private static Date handleDateWithMissingLeadingZeros(String stampString, int dateLength) throws ParseException {
+        if (dateLength == 6) {
+        	synchronized (xep0091Date6DigitFormatter) {
+				return xep0091Date6DigitFormatter.parse(stampString);
+			}
+        }
+        Calendar now = Calendar.getInstance();
+        
+        Calendar oneDigitMonth = parseXEP91Date(stampString, xep0091Date7Digit1MonthFormatter);
+        Calendar twoDigitMonth = parseXEP91Date(stampString, xep0091Date7Digit2MonthFormatter);
+        
+        List<Calendar> dates = filterDatesBefore(now, oneDigitMonth, twoDigitMonth);
+        
+        if (!dates.isEmpty()) {
+            return determineNearestDate(now, dates).getTime();
+        } 
+        return null;
+    }
+
+    private static Calendar parseXEP91Date(String stampString, DateFormat dateFormat) {
+        try {
+            synchronized (dateFormat) {
+                dateFormat.parse(stampString);
+                return dateFormat.getCalendar();
+            }
+        }
+        catch (ParseException e) {
+            return null;
+        }
+    }
+
+    private static List<Calendar> filterDatesBefore(Calendar now, Calendar... dates) {
+        List<Calendar> result = new ArrayList<Calendar>();
+        
+        for (Calendar calendar : dates) {
+            if (calendar != null && calendar.before(now)) {
+                result.add(calendar);
+            }
+        }
+
+        return result;
+    }
+
+    private static Calendar determineNearestDate(final Calendar now, List<Calendar> dates) {
+        
+        Collections.sort(dates, new Comparator<Calendar>() {
+
+            public int compare(Calendar o1, Calendar o2) {
+                Long diff1 = new Long(now.getTimeInMillis() - o1.getTimeInMillis());
+                Long diff2 = new Long(now.getTimeInMillis() - o2.getTimeInMillis());
+                return diff1.compareTo(diff2);
+            }
+            
+        });
+        
+        return dates.get(0);
+    }
+
+    /**
+     * Formats a Date into a XEP-0082 - XMPP Date and Time Profiles string.
+     * 
+     * @param date the time value to be formatted into a time string
+     * @return the formatted time string in XEP-0082 format
+     */
+    public static String formatXEP0082Date(Date date) {
+        synchronized (dateTimeFormatter) {
+            return dateTimeFormatter.format(date);
+        }
+    }
+
+    public static String formatDate(Date toFormat, DateFormatType type)
+    {
+    	return null;
+    }
+    
+    /**
+     * Returns the name portion of a XMPP address. For example, for the
+     * address "matt@jivesoftware.com/Smack", "matt" would be returned. If no
+     * username is present in the address, the empty string will be returned.
+     *
+     * @param XMPPAddress the XMPP address.
+     * @return the name portion of the XMPP address.
+     */
+    public static String parseName(String XMPPAddress) {
+        if (XMPPAddress == null) {
+            return null;
+        }
+        int atIndex = XMPPAddress.lastIndexOf("@");
+        if (atIndex <= 0) {
+            return "";
+        }
+        else {
+            return XMPPAddress.substring(0, atIndex);
+        }
+    }
+
+    /**
+     * Returns the server portion of a XMPP address. For example, for the
+     * address "matt@jivesoftware.com/Smack", "jivesoftware.com" would be returned.
+     * If no server is present in the address, the empty string will be returned.
+     *
+     * @param XMPPAddress the XMPP address.
+     * @return the server portion of the XMPP address.
+     */
+    public static String parseServer(String XMPPAddress) {
+        if (XMPPAddress == null) {
+            return null;
+        }
+        int atIndex = XMPPAddress.lastIndexOf("@");
+        // If the String ends with '@', return the empty string.
+        if (atIndex + 1 > XMPPAddress.length()) {
+            return "";
+        }
+        int slashIndex = XMPPAddress.indexOf("/");
+        if (slashIndex > 0 && slashIndex > atIndex) {
+            return XMPPAddress.substring(atIndex + 1, slashIndex);
+        }
+        else {
+            return XMPPAddress.substring(atIndex + 1);
+        }
+    }
+
+    /**
+     * Returns the resource portion of a XMPP address. For example, for the
+     * address "matt@jivesoftware.com/Smack", "Smack" would be returned. If no
+     * resource is present in the address, the empty string will be returned.
+     *
+     * @param XMPPAddress the XMPP address.
+     * @return the resource portion of the XMPP address.
+     */
+    public static String parseResource(String XMPPAddress) {
+        if (XMPPAddress == null) {
+            return null;
+        }
+        int slashIndex = XMPPAddress.indexOf("/");
+        if (slashIndex + 1 > XMPPAddress.length() || slashIndex < 0) {
+            return "";
+        }
+        else {
+            return XMPPAddress.substring(slashIndex + 1);
+        }
+    }
+
+    /**
+     * Returns the XMPP address with any resource information removed. For example,
+     * for the address "matt@jivesoftware.com/Smack", "matt@jivesoftware.com" would
+     * be returned.
+     *
+     * @param XMPPAddress the XMPP address.
+     * @return the bare XMPP address without resource information.
+     */
+    public static String parseBareAddress(String XMPPAddress) {
+        if (XMPPAddress == null) {
+            return null;
+        }
+        int slashIndex = XMPPAddress.indexOf("/");
+        if (slashIndex < 0) {
+            return XMPPAddress;
+        }
+        else if (slashIndex == 0) {
+            return "";
+        }
+        else {
+            return XMPPAddress.substring(0, slashIndex);
+        }
+    }
+
+    /**
+     * Returns true if jid is a full JID (i.e. a JID with resource part).
+     *
+     * @param jid
+     * @return true if full JID, false otherwise
+     */
+    public static boolean isFullJID(String jid) {
+        if (parseName(jid).length() <= 0 || parseServer(jid).length() <= 0
+                || parseResource(jid).length() <= 0) {
+            return false;
+        }
+        return true;
+    }
+
+    /**
+     * Escapes the node portion of a JID according to "JID Escaping" (JEP-0106).
+     * Escaping replaces characters prohibited by node-prep with escape sequences,
+     * as follows:<p>
+     *
+     * <table border="1">
+     * <tr><td><b>Unescaped Character</b></td><td><b>Encoded Sequence</b></td></tr>
+     * <tr><td>&lt;space&gt;</td><td>\20</td></tr>
+     * <tr><td>"</td><td>\22</td></tr>
+     * <tr><td>&</td><td>\26</td></tr>
+     * <tr><td>'</td><td>\27</td></tr>
+     * <tr><td>/</td><td>\2f</td></tr>
+     * <tr><td>:</td><td>\3a</td></tr>
+     * <tr><td>&lt;</td><td>\3c</td></tr>
+     * <tr><td>&gt;</td><td>\3e</td></tr>
+     * <tr><td>@</td><td>\40</td></tr>
+     * <tr><td>\</td><td>\5c</td></tr>
+     * </table><p>
+     *
+     * This process is useful when the node comes from an external source that doesn't
+     * conform to nodeprep. For example, a username in LDAP may be "Joe Smith". Because
+     * the &lt;space&gt; character isn't a valid part of a node, the username should
+     * be escaped to "Joe\20Smith" before being made into a JID (e.g. "joe\20smith@example.com"
+     * after case-folding, etc. has been applied).<p>
+     *
+     * All node escaping and un-escaping must be performed manually at the appropriate
+     * time; the JID class will not escape or un-escape automatically.
+     *
+     * @param node the node.
+     * @return the escaped version of the node.
+     */
+    public static String escapeNode(String node) {
+        if (node == null) {
+            return null;
+        }
+        StringBuilder buf = new StringBuilder(node.length() + 8);
+        for (int i=0, n=node.length(); i<n; i++) {
+            char c = node.charAt(i);
+            switch (c) {
+                case '"': buf.append("\\22"); break;
+                case '&': buf.append("\\26"); break;
+                case '\'': buf.append("\\27"); break;
+                case '/': buf.append("\\2f"); break;
+                case ':': buf.append("\\3a"); break;
+                case '<': buf.append("\\3c"); break;
+                case '>': buf.append("\\3e"); break;
+                case '@': buf.append("\\40"); break;
+                case '\\': buf.append("\\5c"); break;
+                default: {
+                    if (Character.isWhitespace(c)) {
+                        buf.append("\\20");
+                    }
+                    else {
+                        buf.append(c);
+                    }
+                }
+            }
+        }
+        return buf.toString();
+    }
+
+    /**
+     * Un-escapes the node portion of a JID according to "JID Escaping" (JEP-0106).<p>
+     * Escaping replaces characters prohibited by node-prep with escape sequences,
+     * as follows:<p>
+     *
+     * <table border="1">
+     * <tr><td><b>Unescaped Character</b></td><td><b>Encoded Sequence</b></td></tr>
+     * <tr><td>&lt;space&gt;</td><td>\20</td></tr>
+     * <tr><td>"</td><td>\22</td></tr>
+     * <tr><td>&</td><td>\26</td></tr>
+     * <tr><td>'</td><td>\27</td></tr>
+     * <tr><td>/</td><td>\2f</td></tr>
+     * <tr><td>:</td><td>\3a</td></tr>
+     * <tr><td>&lt;</td><td>\3c</td></tr>
+     * <tr><td>&gt;</td><td>\3e</td></tr>
+     * <tr><td>@</td><td>\40</td></tr>
+     * <tr><td>\</td><td>\5c</td></tr>
+     * </table><p>
+     *
+     * This process is useful when the node comes from an external source that doesn't
+     * conform to nodeprep. For example, a username in LDAP may be "Joe Smith". Because
+     * the &lt;space&gt; character isn't a valid part of a node, the username should
+     * be escaped to "Joe\20Smith" before being made into a JID (e.g. "joe\20smith@example.com"
+     * after case-folding, etc. has been applied).<p>
+     *
+     * All node escaping and un-escaping must be performed manually at the appropriate
+     * time; the JID class will not escape or un-escape automatically.
+     *
+     * @param node the escaped version of the node.
+     * @return the un-escaped version of the node.
+     */
+    public static String unescapeNode(String node) {
+        if (node == null) {
+            return null;
+        }
+        char [] nodeChars = node.toCharArray();
+        StringBuilder buf = new StringBuilder(nodeChars.length);
+        for (int i=0, n=nodeChars.length; i<n; i++) {
+            compare: {
+                char c = node.charAt(i);
+                if (c == '\\' && i+2<n) {
+                    char c2 = nodeChars[i+1];
+                    char c3 = nodeChars[i+2];
+                    if (c2 == '2') {
+                        switch (c3) {
+                            case '0': buf.append(' '); i+=2; break compare;
+                            case '2': buf.append('"'); i+=2; break compare;
+                            case '6': buf.append('&'); i+=2; break compare;
+                            case '7': buf.append('\''); i+=2; break compare;
+                            case 'f': buf.append('/'); i+=2; break compare;
+                        }
+                    }
+                    else if (c2 == '3') {
+                        switch (c3) {
+                            case 'a': buf.append(':'); i+=2; break compare;
+                            case 'c': buf.append('<'); i+=2; break compare;
+                            case 'e': buf.append('>'); i+=2; break compare;
+                        }
+                    }
+                    else if (c2 == '4') {
+                        if (c3 == '0') {
+                            buf.append("@");
+                            i+=2;
+                            break compare;
+                        }
+                    }
+                    else if (c2 == '5') {
+                        if (c3 == 'c') {
+                            buf.append("\\");
+                            i+=2;
+                            break compare;
+                        }
+                    }
+                }
+                buf.append(c);
+            }
+        }
+        return buf.toString();
+    }
+
+    /**
+     * Escapes all necessary characters in the String so that it can be used
+     * in an XML doc.
+     *
+     * @param string the string to escape.
+     * @return the string with appropriate characters escaped.
+     */
+    public static String escapeForXML(String string) {
+        if (string == null) {
+            return null;
+        }
+        char ch;
+        int i=0;
+        int last=0;
+        char[] input = string.toCharArray();
+        int len = input.length;
+        StringBuilder out = new StringBuilder((int)(len*1.3));
+        for (; i < len; i++) {
+            ch = input[i];
+            if (ch > '>') {
+            }
+            else if (ch == '<') {
+                if (i > last) {
+                    out.append(input, last, i - last);
+                }
+                last = i + 1;
+                out.append(LT_ENCODE);
+            }
+            else if (ch == '>') {
+                if (i > last) {
+                    out.append(input, last, i - last);
+                }
+                last = i + 1;
+                out.append(GT_ENCODE);
+            }
+
+            else if (ch == '&') {
+                if (i > last) {
+                    out.append(input, last, i - last);
+                }
+                // Do nothing if the string is of the form &#235; (unicode value)
+                if (!(len > i + 5
+                    && input[i + 1] == '#'
+                    && Character.isDigit(input[i + 2])
+                    && Character.isDigit(input[i + 3])
+                    && Character.isDigit(input[i + 4])
+                    && input[i + 5] == ';')) {
+                        last = i + 1;
+                        out.append(AMP_ENCODE);
+                    }
+            }
+            else if (ch == '"') {
+                if (i > last) {
+                    out.append(input, last, i - last);
+                }
+                last = i + 1;
+                out.append(QUOTE_ENCODE);
+            }
+            else if (ch == '\'') {
+                if (i > last) {
+                    out.append(input, last, i - last);
+                }
+                last = i + 1;
+                out.append(APOS_ENCODE);
+            }
+        }
+        if (last == 0) {
+            return string;
+        }
+        if (i > last) {
+            out.append(input, last, i - last);
+        }
+        return out.toString();
+    }
+
+    /**
+     * Used by the hash method.
+     */
+    private static MessageDigest digest = null;
+
+    /**
+     * Hashes a String using the SHA-1 algorithm and returns the result as a
+     * String of hexadecimal numbers. This method is synchronized to avoid
+     * excessive MessageDigest object creation. If calling this method becomes
+     * a bottleneck in your code, you may wish to maintain a pool of
+     * MessageDigest objects instead of using this method.
+     * <p>
+     * A hash is a one-way function -- that is, given an
+     * input, an output is easily computed. However, given the output, the
+     * input is almost impossible to compute. This is useful for passwords
+     * since we can store the hash and a hacker will then have a very hard time
+     * determining the original password.
+     *
+     * @param data the String to compute the hash of.
+     * @return a hashed version of the passed-in String
+     */
+    public synchronized static String hash(String data) {
+        if (digest == null) {
+            try {
+                digest = MessageDigest.getInstance("SHA-1");
+            }
+            catch (NoSuchAlgorithmException nsae) {
+                System.err.println("Failed to load the SHA-1 MessageDigest. " +
+                "Jive will be unable to function normally.");
+            }
+        }
+        // Now, compute hash.
+        try {
+            digest.update(data.getBytes("UTF-8"));
+        }
+        catch (UnsupportedEncodingException e) {
+            System.err.println(e);
+        }
+        return encodeHex(digest.digest());
+    }
+
+    /**
+     * Encodes an array of bytes as String representation of hexadecimal.
+     *
+     * @param bytes an array of bytes to convert to a hex string.
+     * @return generated hex string.
+     */
+    public static String encodeHex(byte[] bytes) {
+        StringBuilder hex = new StringBuilder(bytes.length * 2);
+
+        for (byte aByte : bytes) {
+            if (((int) aByte & 0xff) < 0x10) {
+                hex.append("0");
+            }
+            hex.append(Integer.toString((int) aByte & 0xff, 16));
+        }
+
+        return hex.toString();
+    }
+
+    /**
+     * Encodes a String as a base64 String.
+     *
+     * @param data a String to encode.
+     * @return a base64 encoded String.
+     */
+    public static String encodeBase64(String data) {
+        byte [] bytes = null;
+        try {
+            bytes = data.getBytes("ISO-8859-1");
+        }
+        catch (UnsupportedEncodingException uee) {
+            uee.printStackTrace();
+        }
+        return encodeBase64(bytes);
+    }
+
+    /**
+     * Encodes a byte array into a base64 String.
+     *
+     * @param data a byte array to encode.
+     * @return a base64 encode String.
+     */
+    public static String encodeBase64(byte[] data) {
+        return encodeBase64(data, false);
+    }
+
+    /**
+     * Encodes a byte array into a bse64 String.
+     *
+     * @param data The byte arry to encode.
+     * @param lineBreaks True if the encoding should contain line breaks and false if it should not.
+     * @return A base64 encoded String.
+     */
+    public static String encodeBase64(byte[] data, boolean lineBreaks) {
+        return encodeBase64(data, 0, data.length, lineBreaks);
+    }
+
+    /**
+     * Encodes a byte array into a bse64 String.
+     *
+     * @param data The byte arry to encode.
+     * @param offset the offset of the bytearray to begin encoding at.
+     * @param len the length of bytes to encode.
+     * @param lineBreaks True if the encoding should contain line breaks and false if it should not.
+     * @return A base64 encoded String.
+     */
+    public static String encodeBase64(byte[] data, int offset, int len, boolean lineBreaks) {
+        return Base64.encodeBytes(data, offset, len, (lineBreaks ?  Base64.NO_OPTIONS : Base64.DONT_BREAK_LINES));
+    }
+
+    /**
+     * Decodes a base64 String.
+     * Unlike Base64.decode() this method does not try to detect and decompress a gzip-compressed input.
+     *
+     * @param data a base64 encoded String to decode.
+     * @return the decoded String.
+     */
+    public static byte[] decodeBase64(String data) {
+        byte[] bytes;
+        try {
+            bytes = data.getBytes("UTF-8");
+        } catch (java.io.UnsupportedEncodingException uee) {
+            bytes = data.getBytes();
+        }
+
+        bytes = Base64.decode(bytes, 0, bytes.length, Base64.NO_OPTIONS);
+        return bytes;
+    }
+
+    /**
+     * Pseudo-random number generator object for use with randomString().
+     * The Random class is not considered to be cryptographically secure, so
+     * only use these random Strings for low to medium security applications.
+     */
+    private static Random randGen = new Random();
+
+    /**
+     * Array of numbers and letters of mixed case. Numbers appear in the list
+     * twice so that there is a more equal chance that a number will be picked.
+     * We can use the array to get a random number or letter by picking a random
+     * array index.
+     */
+    private static char[] numbersAndLetters = ("0123456789abcdefghijklmnopqrstuvwxyz" +
+                    "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ").toCharArray();
+
+    /**
+     * Returns a random String of numbers and letters (lower and upper case)
+     * of the specified length. The method uses the Random class that is
+     * built-in to Java which is suitable for low to medium grade security uses.
+     * This means that the output is only pseudo random, i.e., each number is
+     * mathematically generated so is not truly random.<p>
+     *
+     * The specified length must be at least one. If not, the method will return
+     * null.
+     *
+     * @param length the desired length of the random String to return.
+     * @return a random String of numbers and letters of the specified length.
+     */
+    public static String randomString(int length) {
+        if (length < 1) {
+            return null;
+        }
+        // Create a char buffer to put random letters and numbers in.
+        char [] randBuffer = new char[length];
+        for (int i=0; i<randBuffer.length; i++) {
+            randBuffer[i] = numbersAndLetters[randGen.nextInt(71)];
+        }
+        return new String(randBuffer);
+    }
+
+    private StringUtils() {
+        // Not instantiable.
+    }
+    
+    private static class PatternCouplings {
+    	Pattern pattern;
+    	DateFormat formatter;
+    	boolean needToConvertTimeZone = false;
+    	
+    	public PatternCouplings(Pattern datePattern, DateFormat dateFormat) {
+    		pattern = datePattern;
+    		formatter = dateFormat;
+		}
+
+    	public PatternCouplings(Pattern datePattern, DateFormat dateFormat, boolean shouldConvertToRFC822) {
+    		pattern = datePattern;
+    		formatter = dateFormat;
+    		needToConvertTimeZone = shouldConvertToRFC822;
+		}
+    	
+    	public String convertTime(String dateString) {
+            if (dateString.charAt(dateString.length() - 1) == 'Z') {
+                return dateString.replace("Z", "+0000");
+            }
+            else {
+            	// If the time zone wasn't specified with 'Z', then it's in
+            	// ISO8601 format (i.e. '(+|-)HH:mm')
+            	// RFC822 needs a similar format just without the colon (i.e.
+            	// '(+|-)HHmm)'), so remove it
+                return dateString.replaceAll("([\\+\\-]\\d\\d):(\\d\\d)","$1$2");
+    		}
+    	}
+	}
+
+}
diff --git a/src/org/jivesoftware/smack/util/SyncPacketSend.java b/src/org/jivesoftware/smack/util/SyncPacketSend.java
new file mode 100644
index 0000000..a1c238a
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/SyncPacketSend.java
@@ -0,0 +1,63 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Utility class for doing synchronous calls to the server.  Provides several
+ * methods for sending a packet to the server and waiting for the reply.
+ * 
+ * @author Robin Collier
+ */
+final public class SyncPacketSend
+{
+	private SyncPacketSend()
+	{	}
+	
+	static public Packet getReply(Connection connection, Packet packet, long timeout)
+		throws XMPPException
+	{
+        PacketFilter responseFilter = new PacketIDFilter(packet.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        
+        connection.sendPacket(packet);
+
+        // Wait up to a certain number of seconds for a reply.
+        Packet result = response.nextResult(timeout);
+
+        // Stop queuing results
+        response.cancel();
+
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getError() != null) {
+            throw new XMPPException(result.getError());
+        }
+        return result;
+	}
+
+	static public Packet getReply(Connection connection, Packet packet)
+		throws XMPPException
+	{
+		return getReply(connection, packet, SmackConfiguration.getPacketReplyTimeout());
+	}
+}
diff --git a/src/org/jivesoftware/smack/util/WriterListener.java b/src/org/jivesoftware/smack/util/WriterListener.java
new file mode 100644
index 0000000..dcf56d9
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/WriterListener.java
@@ -0,0 +1,41 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smack.util;
+
+/**
+ * Interface that allows for implementing classes to listen for string writing
+ * events. Listeners are registered with ObservableWriter objects.
+ *
+ * @see ObservableWriter#addWriterListener
+ * @see ObservableWriter#removeWriterListener
+ * 
+ * @author Gaston Dombiak
+ */
+public interface WriterListener {
+
+    /**
+     * Notification that the Writer has written a new string.
+     * 
+     * @param str the written string
+     */
+    public abstract void write(String str);
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/AbstractEmptyIterator.java b/src/org/jivesoftware/smack/util/collections/AbstractEmptyIterator.java
new file mode 100644
index 0000000..c2ec156
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/AbstractEmptyIterator.java
@@ -0,0 +1,89 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.NoSuchElementException;
+
+/**
+ * Provides an implementation of an empty iterator.
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:24 $
+ * @since Commons Collections 3.1
+ */
+abstract class AbstractEmptyIterator <E> {
+
+    /**
+     * Constructor.
+     */
+    protected AbstractEmptyIterator() {
+        super();
+    }
+
+    public boolean hasNext() {
+        return false;
+    }
+
+    public E next() {
+        throw new NoSuchElementException("Iterator contains no elements");
+    }
+
+    public boolean hasPrevious() {
+        return false;
+    }
+
+    public E previous() {
+        throw new NoSuchElementException("Iterator contains no elements");
+    }
+
+    public int nextIndex() {
+        return 0;
+    }
+
+    public int previousIndex() {
+        return -1;
+    }
+
+    public void add(E obj) {
+        throw new UnsupportedOperationException("add() not supported for empty Iterator");
+    }
+
+    public void set(E obj) {
+        throw new IllegalStateException("Iterator contains no elements");
+    }
+
+    public void remove() {
+        throw new IllegalStateException("Iterator contains no elements");
+    }
+
+    public E getKey() {
+        throw new IllegalStateException("Iterator contains no elements");
+    }
+
+    public E getValue() {
+        throw new IllegalStateException("Iterator contains no elements");
+    }
+
+    public E setValue(E value) {
+        throw new IllegalStateException("Iterator contains no elements");
+    }
+
+    public void reset() {
+        // do nothing
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/AbstractHashedMap.java b/src/org/jivesoftware/smack/util/collections/AbstractHashedMap.java
new file mode 100644
index 0000000..f6fb34a
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/AbstractHashedMap.java
@@ -0,0 +1,1338 @@
+// GenericsNote: Converted -- However, null keys will now be represented in the internal structures, a big change.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.util.*;
+
+/**
+ * An abstract implementation of a hash-based map which provides numerous points for
+ * subclasses to override.
+ * <p/>
+ * This class implements all the features necessary for a subclass hash-based map.
+ * Key-value entries are stored in instances of the <code>HashEntry</code> class,
+ * which can be overridden and replaced. The iterators can similarly be replaced,
+ * without the need to replace the KeySet, EntrySet and Values view classes.
+ * <p/>
+ * Overridable methods are provided to change the default hashing behaviour, and
+ * to change how entries are added to and removed from the map. Hopefully, all you
+ * need for unusual subclasses is here.
+ * <p/>
+ * NOTE: From Commons Collections 3.1 this class extends AbstractMap.
+ * This is to provide backwards compatibility for ReferenceMap between v3.0 and v3.1.
+ * This extends clause will be removed in v4.0.
+ *
+ * @author java util HashMap
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @since Commons Collections 3.0
+ */
+public class AbstractHashedMap <K,V> extends AbstractMap<K, V> implements IterableMap<K, V> {
+
+    protected static final String NO_NEXT_ENTRY = "No next() entry in the iteration";
+    protected static final String NO_PREVIOUS_ENTRY = "No previous() entry in the iteration";
+    protected static final String REMOVE_INVALID = "remove() can only be called once after next()";
+    protected static final String GETKEY_INVALID = "getKey() can only be called after next() and before remove()";
+    protected static final String GETVALUE_INVALID = "getValue() can only be called after next() and before remove()";
+    protected static final String SETVALUE_INVALID = "setValue() can only be called after next() and before remove()";
+
+    /**
+     * The default capacity to use
+     */
+    protected static final int DEFAULT_CAPACITY = 16;
+    /**
+     * The default threshold to use
+     */
+    protected static final int DEFAULT_THRESHOLD = 12;
+    /**
+     * The default load factor to use
+     */
+    protected static final float DEFAULT_LOAD_FACTOR = 0.75f;
+    /**
+     * The maximum capacity allowed
+     */
+    protected static final int MAXIMUM_CAPACITY = 1 << 30;
+    /**
+     * An object for masking null
+     */
+    protected static final Object NULL = new Object();
+
+    /**
+     * Load factor, normally 0.75
+     */
+    protected transient float loadFactor;
+    /**
+     * The size of the map
+     */
+    protected transient int size;
+    /**
+     * Map entries
+     */
+    protected transient HashEntry<K, V>[] data;
+    /**
+     * Size at which to rehash
+     */
+    protected transient int threshold;
+    /**
+     * Modification count for iterators
+     */
+    protected transient int modCount;
+    /**
+     * Entry set
+     */
+    protected transient EntrySet<K, V> entrySet;
+    /**
+     * Key set
+     */
+    protected transient KeySet<K, V> keySet;
+    /**
+     * Values
+     */
+    protected transient Values<K, V> values;
+
+    /**
+     * Constructor only used in deserialization, do not use otherwise.
+     */
+    protected AbstractHashedMap() {
+        super();
+    }
+
+    /**
+     * Constructor which performs no validation on the passed in parameters.
+     *
+     * @param initialCapacity the initial capacity, must be a power of two
+     * @param loadFactor      the load factor, must be &gt; 0.0f and generally &lt; 1.0f
+     * @param threshold       the threshold, must be sensible
+     */
+    protected AbstractHashedMap(int initialCapacity, float loadFactor, int threshold) {
+        super();
+        this.loadFactor = loadFactor;
+        this.data = new HashEntry[initialCapacity];
+        this.threshold = threshold;
+        init();
+    }
+
+    /**
+     * Constructs a new, empty map with the specified initial capacity and
+     * default load factor.
+     *
+     * @param initialCapacity the initial capacity
+     * @throws IllegalArgumentException if the initial capacity is less than one
+     */
+    protected AbstractHashedMap(int initialCapacity) {
+        this(initialCapacity, DEFAULT_LOAD_FACTOR);
+    }
+
+    /**
+     * Constructs a new, empty map with the specified initial capacity and
+     * load factor.
+     *
+     * @param initialCapacity the initial capacity
+     * @param loadFactor      the load factor
+     * @throws IllegalArgumentException if the initial capacity is less than one
+     * @throws IllegalArgumentException if the load factor is less than or equal to zero
+     */
+    protected AbstractHashedMap(int initialCapacity, float loadFactor) {
+        super();
+        if (initialCapacity < 1) {
+            throw new IllegalArgumentException("Initial capacity must be greater than 0");
+        }
+        if (loadFactor <= 0.0f || Float.isNaN(loadFactor)) {
+            throw new IllegalArgumentException("Load factor must be greater than 0");
+        }
+        this.loadFactor = loadFactor;
+        this.threshold = calculateThreshold(initialCapacity, loadFactor);
+        initialCapacity = calculateNewCapacity(initialCapacity);
+        this.data = new HashEntry[initialCapacity];
+        init();
+    }
+
+    /**
+     * Constructor copying elements from another map.
+     *
+     * @param map the map to copy
+     * @throws NullPointerException if the map is null
+     */
+    protected AbstractHashedMap(Map<? extends K, ? extends V> map) {
+        this(Math.max(2 * map.size(), DEFAULT_CAPACITY), DEFAULT_LOAD_FACTOR);
+        putAll(map);
+    }
+
+    /**
+     * Initialise subclasses during construction, cloning or deserialization.
+     */
+    protected void init() {
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the value mapped to the key specified.
+     *
+     * @param key the key
+     * @return the mapped value, null if no match
+     */
+    public V get(Object key) {
+        int hashCode = hash((key == null) ? NULL : key);
+        HashEntry<K, V> entry = data[hashIndex(hashCode, data.length)]; // no local for hash index
+        while (entry != null) {
+            if (entry.hashCode == hashCode && isEqualKey(key, entry.key)) {
+                return entry.getValue();
+            }
+            entry = entry.next;
+        }
+        return null;
+    }
+
+    /**
+     * Gets the size of the map.
+     *
+     * @return the size
+     */
+    public int size() {
+        return size;
+    }
+
+    /**
+     * Checks whether the map is currently empty.
+     *
+     * @return true if the map is currently size zero
+     */
+    public boolean isEmpty() {
+        return (size == 0);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Checks whether the map contains the specified key.
+     *
+     * @param key the key to search for
+     * @return true if the map contains the key
+     */
+    public boolean containsKey(Object key) {
+        int hashCode = hash((key == null) ? NULL : key);
+        HashEntry entry = data[hashIndex(hashCode, data.length)]; // no local for hash index
+        while (entry != null) {
+            if (entry.hashCode == hashCode && isEqualKey(key, entry.getKey())) {
+                return true;
+            }
+            entry = entry.next;
+        }
+        return false;
+    }
+
+    /**
+     * Checks whether the map contains the specified value.
+     *
+     * @param value the value to search for
+     * @return true if the map contains the value
+     */
+    public boolean containsValue(Object value) {
+        if (value == null) {
+            for (int i = 0, isize = data.length; i < isize; i++) {
+                HashEntry entry = data[i];
+                while (entry != null) {
+                    if (entry.getValue() == null) {
+                        return true;
+                    }
+                    entry = entry.next;
+                }
+            }
+        } else {
+            for (int i = 0, isize = data.length; i < isize; i++) {
+                HashEntry entry = data[i];
+                while (entry != null) {
+                    if (isEqualValue(value, entry.getValue())) {
+                        return true;
+                    }
+                    entry = entry.next;
+                }
+            }
+        }
+        return false;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Puts a key-value mapping into this map.
+     *
+     * @param key   the key to add
+     * @param value the value to add
+     * @return the value previously mapped to this key, null if none
+     */
+    public V put(K key, V value) {
+        int hashCode = hash((key == null) ? NULL : key);
+        int index = hashIndex(hashCode, data.length);
+        HashEntry<K, V> entry = data[index];
+        while (entry != null) {
+            if (entry.hashCode == hashCode && isEqualKey(key, entry.getKey())) {
+                V oldValue = entry.getValue();
+                updateEntry(entry, value);
+                return oldValue;
+            }
+            entry = entry.next;
+        }
+        addMapping(index, hashCode, key, value);
+        return null;
+    }
+
+    /**
+     * Puts all the values from the specified map into this map.
+     * <p/>
+     * This implementation iterates around the specified map and
+     * uses {@link #put(Object, Object)}.
+     *
+     * @param map the map to add
+     * @throws NullPointerException if the map is null
+     */
+    public void putAll(Map<? extends K, ? extends V> map) {
+        int mapSize = map.size();
+        if (mapSize == 0) {
+            return;
+        }
+        int newSize = (int) ((size + mapSize) / loadFactor + 1);
+        ensureCapacity(calculateNewCapacity(newSize));
+        // Have to cast here because of compiler inference problems.
+        for (Iterator it = map.entrySet().iterator(); it.hasNext();) {
+            Map.Entry<? extends K, ? extends V> entry = (Map.Entry<? extends K, ? extends V>) it.next();
+            put(entry.getKey(), entry.getValue());
+        }
+    }
+
+    /**
+     * Removes the specified mapping from this map.
+     *
+     * @param key the mapping to remove
+     * @return the value mapped to the removed key, null if key not in map
+     */
+    public V remove(Object key) {
+        int hashCode = hash((key == null) ? NULL : key);
+        int index = hashIndex(hashCode, data.length);
+        HashEntry<K, V> entry = data[index];
+        HashEntry<K, V> previous = null;
+        while (entry != null) {
+            if (entry.hashCode == hashCode && isEqualKey(key, entry.getKey())) {
+                V oldValue = entry.getValue();
+                removeMapping(entry, index, previous);
+                return oldValue;
+            }
+            previous = entry;
+            entry = entry.next;
+        }
+        return null;
+    }
+
+    /**
+     * Clears the map, resetting the size to zero and nullifying references
+     * to avoid garbage collection issues.
+     */
+    public void clear() {
+        modCount++;
+        HashEntry[] data = this.data;
+        for (int i = data.length - 1; i >= 0; i--) {
+            data[i] = null;
+        }
+        size = 0;
+    }
+
+    /**
+     * Gets the hash code for the key specified.
+     * This implementation uses the additional hashing routine from JDK1.4.
+     * Subclasses can override this to return alternate hash codes.
+     *
+     * @param key the key to get a hash code for
+     * @return the hash code
+     */
+    protected int hash(Object key) {
+        // same as JDK 1.4
+        int h = key.hashCode();
+        h += ~(h << 9);
+        h ^= (h >>> 14);
+        h += (h << 4);
+        h ^= (h >>> 10);
+        return h;
+    }
+
+    /**
+     * Compares two keys, in internal converted form, to see if they are equal.
+     * This implementation uses the equals method.
+     * Subclasses can override this to match differently.
+     *
+     * @param key1 the first key to compare passed in from outside
+     * @param key2 the second key extracted from the entry via <code>entry.key</code>
+     * @return true if equal
+     */
+    protected boolean isEqualKey(Object key1, Object key2) {
+        return (key1 == key2 || ((key1 != null) && key1.equals(key2)));
+    }
+
+    /**
+     * Compares two values, in external form, to see if they are equal.
+     * This implementation uses the equals method and assumes neither value is null.
+     * Subclasses can override this to match differently.
+     *
+     * @param value1 the first value to compare passed in from outside
+     * @param value2 the second value extracted from the entry via <code>getValue()</code>
+     * @return true if equal
+     */
+    protected boolean isEqualValue(Object value1, Object value2) {
+        return (value1 == value2 || value1.equals(value2));
+    }
+
+    /**
+     * Gets the index into the data storage for the hashCode specified.
+     * This implementation uses the least significant bits of the hashCode.
+     * Subclasses can override this to return alternate bucketing.
+     *
+     * @param hashCode the hash code to use
+     * @param dataSize the size of the data to pick a bucket from
+     * @return the bucket index
+     */
+    protected int hashIndex(int hashCode, int dataSize) {
+        return hashCode & (dataSize - 1);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the entry mapped to the key specified.
+     * <p/>
+     * This method exists for subclasses that may need to perform a multi-step
+     * process accessing the entry. The public methods in this class don't use this
+     * method to gain a small performance boost.
+     *
+     * @param key the key
+     * @return the entry, null if no match
+     */
+    protected HashEntry<K, V> getEntry(Object key) {
+        int hashCode = hash((key == null) ? NULL : key);
+        HashEntry<K, V> entry = data[hashIndex(hashCode, data.length)]; // no local for hash index
+        while (entry != null) {
+            if (entry.hashCode == hashCode && isEqualKey(key, entry.getKey())) {
+                return entry;
+            }
+            entry = entry.next;
+        }
+        return null;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Updates an existing key-value mapping to change the value.
+     * <p/>
+     * This implementation calls <code>setValue()</code> on the entry.
+     * Subclasses could override to handle changes to the map.
+     *
+     * @param entry    the entry to update
+     * @param newValue the new value to store
+     */
+    protected void updateEntry(HashEntry<K, V> entry, V newValue) {
+        entry.setValue(newValue);
+    }
+
+    /**
+     * Reuses an existing key-value mapping, storing completely new data.
+     * <p/>
+     * This implementation sets all the data fields on the entry.
+     * Subclasses could populate additional entry fields.
+     *
+     * @param entry     the entry to update, not null
+     * @param hashIndex the index in the data array
+     * @param hashCode  the hash code of the key to add
+     * @param key       the key to add
+     * @param value     the value to add
+     */
+    protected void reuseEntry(HashEntry<K, V> entry, int hashIndex, int hashCode, K key, V value) {
+        entry.next = data[hashIndex];
+        entry.hashCode = hashCode;
+        entry.key = key;
+        entry.value = value;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Adds a new key-value mapping into this map.
+     * <p/>
+     * This implementation calls <code>createEntry()</code>, <code>addEntry()</code>
+     * and <code>checkCapacity()</code>.
+     * It also handles changes to <code>modCount</code> and <code>size</code>.
+     * Subclasses could override to fully control adds to the map.
+     *
+     * @param hashIndex the index into the data array to store at
+     * @param hashCode  the hash code of the key to add
+     * @param key       the key to add
+     * @param value     the value to add
+     */
+    protected void addMapping(int hashIndex, int hashCode, K key, V value) {
+        modCount++;
+        HashEntry<K, V> entry = createEntry(data[hashIndex], hashCode, key, value);
+        addEntry(entry, hashIndex);
+        size++;
+        checkCapacity();
+    }
+
+    /**
+     * Creates an entry to store the key-value data.
+     * <p/>
+     * This implementation creates a new HashEntry instance.
+     * Subclasses can override this to return a different storage class,
+     * or implement caching.
+     *
+     * @param next     the next entry in sequence
+     * @param hashCode the hash code to use
+     * @param key      the key to store
+     * @param value    the value to store
+     * @return the newly created entry
+     */
+    protected HashEntry<K, V> createEntry(HashEntry<K, V> next, int hashCode, K key, V value) {
+        return new HashEntry<K, V>(next, hashCode, key, value);
+    }
+
+    /**
+     * Adds an entry into this map.
+     * <p/>
+     * This implementation adds the entry to the data storage table.
+     * Subclasses could override to handle changes to the map.
+     *
+     * @param entry     the entry to add
+     * @param hashIndex the index into the data array to store at
+     */
+    protected void addEntry(HashEntry<K, V> entry, int hashIndex) {
+        data[hashIndex] = entry;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Removes a mapping from the map.
+     * <p/>
+     * This implementation calls <code>removeEntry()</code> and <code>destroyEntry()</code>.
+     * It also handles changes to <code>modCount</code> and <code>size</code>.
+     * Subclasses could override to fully control removals from the map.
+     *
+     * @param entry     the entry to remove
+     * @param hashIndex the index into the data structure
+     * @param previous  the previous entry in the chain
+     */
+    protected void removeMapping(HashEntry<K, V> entry, int hashIndex, HashEntry<K, V> previous) {
+        modCount++;
+        removeEntry(entry, hashIndex, previous);
+        size--;
+        destroyEntry(entry);
+    }
+
+    /**
+     * Removes an entry from the chain stored in a particular index.
+     * <p/>
+     * This implementation removes the entry from the data storage table.
+     * The size is not updated.
+     * Subclasses could override to handle changes to the map.
+     *
+     * @param entry     the entry to remove
+     * @param hashIndex the index into the data structure
+     * @param previous  the previous entry in the chain
+     */
+    protected void removeEntry(HashEntry<K, V> entry, int hashIndex, HashEntry<K, V> previous) {
+        if (previous == null) {
+            data[hashIndex] = entry.next;
+        } else {
+            previous.next = entry.next;
+        }
+    }
+
+    /**
+     * Kills an entry ready for the garbage collector.
+     * <p/>
+     * This implementation prepares the HashEntry for garbage collection.
+     * Subclasses can override this to implement caching (override clear as well).
+     *
+     * @param entry the entry to destroy
+     */
+    protected void destroyEntry(HashEntry<K, V> entry) {
+        entry.next = null;
+        entry.key = null;
+        entry.value = null;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Checks the capacity of the map and enlarges it if necessary.
+     * <p/>
+     * This implementation uses the threshold to check if the map needs enlarging
+     */
+    protected void checkCapacity() {
+        if (size >= threshold) {
+            int newCapacity = data.length * 2;
+            if (newCapacity <= MAXIMUM_CAPACITY) {
+                ensureCapacity(newCapacity);
+            }
+        }
+    }
+
+    /**
+     * Changes the size of the data structure to the capacity proposed.
+     *
+     * @param newCapacity the new capacity of the array (a power of two, less or equal to max)
+     */
+    protected void ensureCapacity(int newCapacity) {
+        int oldCapacity = data.length;
+        if (newCapacity <= oldCapacity) {
+            return;
+        }
+        if (size == 0) {
+            threshold = calculateThreshold(newCapacity, loadFactor);
+            data = new HashEntry[newCapacity];
+        } else {
+            HashEntry<K, V> oldEntries[] = data;
+            HashEntry<K, V> newEntries[] = new HashEntry[newCapacity];
+
+            modCount++;
+            for (int i = oldCapacity - 1; i >= 0; i--) {
+                HashEntry<K, V> entry = oldEntries[i];
+                if (entry != null) {
+                    oldEntries[i] = null;  // gc
+                    do {
+                        HashEntry<K, V> next = entry.next;
+                        int index = hashIndex(entry.hashCode, newCapacity);
+                        entry.next = newEntries[index];
+                        newEntries[index] = entry;
+                        entry = next;
+                    } while (entry != null);
+                }
+            }
+            threshold = calculateThreshold(newCapacity, loadFactor);
+            data = newEntries;
+        }
+    }
+
+    /**
+     * Calculates the new capacity of the map.
+     * This implementation normalizes the capacity to a power of two.
+     *
+     * @param proposedCapacity the proposed capacity
+     * @return the normalized new capacity
+     */
+    protected int calculateNewCapacity(int proposedCapacity) {
+        int newCapacity = 1;
+        if (proposedCapacity > MAXIMUM_CAPACITY) {
+            newCapacity = MAXIMUM_CAPACITY;
+        } else {
+            while (newCapacity < proposedCapacity) {
+                newCapacity <<= 1;  // multiply by two
+            }
+            if (newCapacity > MAXIMUM_CAPACITY) {
+                newCapacity = MAXIMUM_CAPACITY;
+            }
+        }
+        return newCapacity;
+    }
+
+    /**
+     * Calculates the new threshold of the map, where it will be resized.
+     * This implementation uses the load factor.
+     *
+     * @param newCapacity the new capacity
+     * @param factor      the load factor
+     * @return the new resize threshold
+     */
+    protected int calculateThreshold(int newCapacity, float factor) {
+        return (int) (newCapacity * factor);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the <code>next</code> field from a <code>HashEntry</code>.
+     * Used in subclasses that have no visibility of the field.
+     *
+     * @param entry the entry to query, must not be null
+     * @return the <code>next</code> field of the entry
+     * @throws NullPointerException if the entry is null
+     * @since Commons Collections 3.1
+     */
+    protected HashEntry<K, V> entryNext(HashEntry<K, V> entry) {
+        return entry.next;
+    }
+
+    /**
+     * Gets the <code>hashCode</code> field from a <code>HashEntry</code>.
+     * Used in subclasses that have no visibility of the field.
+     *
+     * @param entry the entry to query, must not be null
+     * @return the <code>hashCode</code> field of the entry
+     * @throws NullPointerException if the entry is null
+     * @since Commons Collections 3.1
+     */
+    protected int entryHashCode(HashEntry<K, V> entry) {
+        return entry.hashCode;
+    }
+
+    /**
+     * Gets the <code>key</code> field from a <code>HashEntry</code>.
+     * Used in subclasses that have no visibility of the field.
+     *
+     * @param entry the entry to query, must not be null
+     * @return the <code>key</code> field of the entry
+     * @throws NullPointerException if the entry is null
+     * @since Commons Collections 3.1
+     */
+    protected K entryKey(HashEntry<K, V> entry) {
+        return entry.key;
+    }
+
+    /**
+     * Gets the <code>value</code> field from a <code>HashEntry</code>.
+     * Used in subclasses that have no visibility of the field.
+     *
+     * @param entry the entry to query, must not be null
+     * @return the <code>value</code> field of the entry
+     * @throws NullPointerException if the entry is null
+     * @since Commons Collections 3.1
+     */
+    protected V entryValue(HashEntry<K, V> entry) {
+        return entry.value;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets an iterator over the map.
+     * Changes made to the iterator affect this map.
+     * <p/>
+     * A MapIterator returns the keys in the map. It also provides convenient
+     * methods to get the key and value, and set the value.
+     * It avoids the need to create an entrySet/keySet/values object.
+     * It also avoids creating the Map.Entry object.
+     *
+     * @return the map iterator
+     */
+    public MapIterator<K, V> mapIterator() {
+        if (size == 0) {
+            return EmptyMapIterator.INSTANCE;
+        }
+        return new HashMapIterator<K, V>(this);
+    }
+
+    /**
+     * MapIterator implementation.
+     */
+    protected static class HashMapIterator <K,V> extends HashIterator<K, V> implements MapIterator<K, V> {
+
+        protected HashMapIterator(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public K next() {
+            return super.nextEntry().getKey();
+        }
+
+        public K getKey() {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.GETKEY_INVALID);
+            }
+            return current.getKey();
+        }
+
+        public V getValue() {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.GETVALUE_INVALID);
+            }
+            return current.getValue();
+        }
+
+        public V setValue(V value) {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.SETVALUE_INVALID);
+            }
+            return current.setValue(value);
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the entrySet view of the map.
+     * Changes made to the view affect this map.
+     * To simply iterate through the entries, use {@link #mapIterator()}.
+     *
+     * @return the entrySet view
+     */
+    public Set<Map.Entry<K, V>> entrySet() {
+        if (entrySet == null) {
+            entrySet = new EntrySet<K, V>(this);
+        }
+        return entrySet;
+    }
+
+    /**
+     * Creates an entry set iterator.
+     * Subclasses can override this to return iterators with different properties.
+     *
+     * @return the entrySet iterator
+     */
+    protected Iterator<Map.Entry<K, V>> createEntrySetIterator() {
+        if (size() == 0) {
+            return EmptyIterator.INSTANCE;
+        }
+        return new EntrySetIterator<K, V>(this);
+    }
+
+    /**
+     * EntrySet implementation.
+     */
+    protected static class EntrySet <K,V> extends AbstractSet<Map.Entry<K, V>> {
+        /**
+         * The parent map
+         */
+        protected final AbstractHashedMap<K, V> parent;
+
+        protected EntrySet(AbstractHashedMap<K, V> parent) {
+            super();
+            this.parent = parent;
+        }
+
+        public int size() {
+            return parent.size();
+        }
+
+        public void clear() {
+            parent.clear();
+        }
+
+        public boolean contains(Map.Entry<K, V> entry) {
+            Map.Entry<K, V> e = entry;
+            Entry<K, V> match = parent.getEntry(e.getKey());
+            return (match != null && match.equals(e));
+        }
+
+        public boolean remove(Object obj) {
+            if (obj instanceof Map.Entry == false) {
+                return false;
+            }
+            if (contains(obj) == false) {
+                return false;
+            }
+            Map.Entry<K, V> entry = (Map.Entry<K, V>) obj;
+            K key = entry.getKey();
+            parent.remove(key);
+            return true;
+        }
+
+        public Iterator<Map.Entry<K, V>> iterator() {
+            return parent.createEntrySetIterator();
+        }
+    }
+
+    /**
+     * EntrySet iterator.
+     */
+    protected static class EntrySetIterator <K,V> extends HashIterator<K, V> implements Iterator<Map.Entry<K, V>> {
+
+        protected EntrySetIterator(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public HashEntry<K, V> next() {
+            return super.nextEntry();
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the keySet view of the map.
+     * Changes made to the view affect this map.
+     * To simply iterate through the keys, use {@link #mapIterator()}.
+     *
+     * @return the keySet view
+     */
+    public Set<K> keySet() {
+        if (keySet == null) {
+            keySet = new KeySet<K, V>(this);
+        }
+        return keySet;
+    }
+
+    /**
+     * Creates a key set iterator.
+     * Subclasses can override this to return iterators with different properties.
+     *
+     * @return the keySet iterator
+     */
+    protected Iterator<K> createKeySetIterator() {
+        if (size() == 0) {
+            return EmptyIterator.INSTANCE;
+        }
+        return new KeySetIterator<K, V>(this);
+    }
+
+    /**
+     * KeySet implementation.
+     */
+    protected static class KeySet <K,V> extends AbstractSet<K> {
+        /**
+         * The parent map
+         */
+        protected final AbstractHashedMap<K, V> parent;
+
+        protected KeySet(AbstractHashedMap<K, V> parent) {
+            super();
+            this.parent = parent;
+        }
+
+        public int size() {
+            return parent.size();
+        }
+
+        public void clear() {
+            parent.clear();
+        }
+
+        public boolean contains(Object key) {
+            return parent.containsKey(key);
+        }
+
+        public boolean remove(Object key) {
+            boolean result = parent.containsKey(key);
+            parent.remove(key);
+            return result;
+        }
+
+        public Iterator<K> iterator() {
+            return parent.createKeySetIterator();
+        }
+    }
+
+    /**
+     * KeySet iterator.
+     */
+    protected static class KeySetIterator <K,V> extends HashIterator<K, V> implements Iterator<K> {
+
+        protected KeySetIterator(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public K next() {
+            return super.nextEntry().getKey();
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the values view of the map.
+     * Changes made to the view affect this map.
+     * To simply iterate through the values, use {@link #mapIterator()}.
+     *
+     * @return the values view
+     */
+    public Collection<V> values() {
+        if (values == null) {
+            values = new Values(this);
+        }
+        return values;
+    }
+
+    /**
+     * Creates a values iterator.
+     * Subclasses can override this to return iterators with different properties.
+     *
+     * @return the values iterator
+     */
+    protected Iterator<V> createValuesIterator() {
+        if (size() == 0) {
+            return EmptyIterator.INSTANCE;
+        }
+        return new ValuesIterator<K, V>(this);
+    }
+
+    /**
+     * Values implementation.
+     */
+    protected static class Values <K,V> extends AbstractCollection<V> {
+        /**
+         * The parent map
+         */
+        protected final AbstractHashedMap<K, V> parent;
+
+        protected Values(AbstractHashedMap<K, V> parent) {
+            super();
+            this.parent = parent;
+        }
+
+        public int size() {
+            return parent.size();
+        }
+
+        public void clear() {
+            parent.clear();
+        }
+
+        public boolean contains(Object value) {
+            return parent.containsValue(value);
+        }
+
+        public Iterator<V> iterator() {
+            return parent.createValuesIterator();
+        }
+    }
+
+    /**
+     * Values iterator.
+     */
+    protected static class ValuesIterator <K,V> extends HashIterator<K, V> implements Iterator<V> {
+
+        protected ValuesIterator(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public V next() {
+            return super.nextEntry().getValue();
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * HashEntry used to store the data.
+     * <p/>
+     * If you subclass <code>AbstractHashedMap</code> but not <code>HashEntry</code>
+     * then you will not be able to access the protected fields.
+     * The <code>entryXxx()</code> methods on <code>AbstractHashedMap</code> exist
+     * to provide the necessary access.
+     */
+    protected static class HashEntry <K,V> implements Map.Entry<K, V>, KeyValue<K, V> {
+        /**
+         * The next entry in the hash chain
+         */
+        protected HashEntry<K, V> next;
+        /**
+         * The hash code of the key
+         */
+        protected int hashCode;
+        /**
+         * The key
+         */
+        private K key;
+        /**
+         * The value
+         */
+        private V value;
+
+        protected HashEntry(HashEntry<K, V> next, int hashCode, K key, V value) {
+            super();
+            this.next = next;
+            this.hashCode = hashCode;
+            this.key = key;
+            this.value = value;
+        }
+
+        public K getKey() {
+            return key;
+        }
+
+        public void setKey(K key) {
+            this.key = key;
+        }
+
+        public V getValue() {
+            return value;
+        }
+
+        public V setValue(V value) {
+            V old = this.value;
+            this.value = value;
+            return old;
+        }
+
+        public boolean equals(Object obj) {
+            if (obj == this) {
+                return true;
+            }
+            if (obj instanceof Map.Entry == false) {
+                return false;
+            }
+            Map.Entry other = (Map.Entry) obj;
+            return (getKey() == null ? other.getKey() == null : getKey().equals(other.getKey())) && (getValue() == null ? other.getValue() == null : getValue().equals(other.getValue()));
+        }
+
+        public int hashCode() {
+            return (getKey() == null ? 0 : getKey().hashCode()) ^ (getValue() == null ? 0 : getValue().hashCode());
+        }
+
+        public String toString() {
+            return new StringBuilder().append(getKey()).append('=').append(getValue()).toString();
+        }
+    }
+
+    /**
+     * Base Iterator
+     */
+    protected static abstract class HashIterator <K,V> {
+
+        /**
+         * The parent map
+         */
+        protected final AbstractHashedMap parent;
+        /**
+         * The current index into the array of buckets
+         */
+        protected int hashIndex;
+        /**
+         * The last returned entry
+         */
+        protected HashEntry<K, V> last;
+        /**
+         * The next entry
+         */
+        protected HashEntry<K, V> next;
+        /**
+         * The modification count expected
+         */
+        protected int expectedModCount;
+
+        protected HashIterator(AbstractHashedMap<K, V> parent) {
+            super();
+            this.parent = parent;
+            HashEntry<K, V>[] data = parent.data;
+            int i = data.length;
+            HashEntry<K, V> next = null;
+            while (i > 0 && next == null) {
+                next = data[--i];
+            }
+            this.next = next;
+            this.hashIndex = i;
+            this.expectedModCount = parent.modCount;
+        }
+
+        public boolean hasNext() {
+            return (next != null);
+        }
+
+        protected HashEntry<K, V> nextEntry() {
+            if (parent.modCount != expectedModCount) {
+                throw new ConcurrentModificationException();
+            }
+            HashEntry<K, V> newCurrent = next;
+            if (newCurrent == null) {
+                throw new NoSuchElementException(AbstractHashedMap.NO_NEXT_ENTRY);
+            }
+            HashEntry<K, V>[] data = parent.data;
+            int i = hashIndex;
+            HashEntry<K, V> n = newCurrent.next;
+            while (n == null && i > 0) {
+                n = data[--i];
+            }
+            next = n;
+            hashIndex = i;
+            last = newCurrent;
+            return newCurrent;
+        }
+
+        protected HashEntry<K, V> currentEntry() {
+            return last;
+        }
+
+        public void remove() {
+            if (last == null) {
+                throw new IllegalStateException(AbstractHashedMap.REMOVE_INVALID);
+            }
+            if (parent.modCount != expectedModCount) {
+                throw new ConcurrentModificationException();
+            }
+            parent.remove(last.getKey());
+            last = null;
+            expectedModCount = parent.modCount;
+        }
+
+        public String toString() {
+            if (last != null) {
+                return "Iterator[" + last.getKey() + "=" + last.getValue() + "]";
+            } else {
+                return "Iterator[]";
+            }
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Writes the map data to the stream. This method must be overridden if a
+     * subclass must be setup before <code>put()</code> is used.
+     * <p/>
+     * Serialization is not one of the JDK's nicest topics. Normal serialization will
+     * initialise the superclass before the subclass. Sometimes however, this isn't
+     * what you want, as in this case the <code>put()</code> method on read can be
+     * affected by subclass state.
+     * <p/>
+     * The solution adopted here is to serialize the state data of this class in
+     * this protected method. This method must be called by the
+     * <code>writeObject()</code> of the first serializable subclass.
+     * <p/>
+     * Subclasses may override if they have a specific field that must be present
+     * on read before this implementation will work. Generally, the read determines
+     * what must be serialized here, if anything.
+     *
+     * @param out the output stream
+     */
+    protected void doWriteObject(ObjectOutputStream out) throws IOException {
+        out.writeFloat(loadFactor);
+        out.writeInt(data.length);
+        out.writeInt(size);
+        for (MapIterator it = mapIterator(); it.hasNext();) {
+            out.writeObject(it.next());
+            out.writeObject(it.getValue());
+        }
+    }
+
+    /**
+     * Reads the map data from the stream. This method must be overridden if a
+     * subclass must be setup before <code>put()</code> is used.
+     * <p/>
+     * Serialization is not one of the JDK's nicest topics. Normal serialization will
+     * initialise the superclass before the subclass. Sometimes however, this isn't
+     * what you want, as in this case the <code>put()</code> method on read can be
+     * affected by subclass state.
+     * <p/>
+     * The solution adopted here is to deserialize the state data of this class in
+     * this protected method. This method must be called by the
+     * <code>readObject()</code> of the first serializable subclass.
+     * <p/>
+     * Subclasses may override if the subclass has a specific field that must be present
+     * before <code>put()</code> or <code>calculateThreshold()</code> will work correctly.
+     *
+     * @param in the input stream
+     */
+    protected void doReadObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
+        loadFactor = in.readFloat();
+        int capacity = in.readInt();
+        int size = in.readInt();
+        init();
+        data = new HashEntry[capacity];
+        for (int i = 0; i < size; i++) {
+            K key = (K) in.readObject();
+            V value = (V) in.readObject();
+            put(key, value);
+        }
+        threshold = calculateThreshold(data.length, loadFactor);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Clones the map without cloning the keys or values.
+     * <p/>
+     * To implement <code>clone()</code>, a subclass must implement the
+     * <code>Cloneable</code> interface and make this method public.
+     *
+     * @return a shallow clone
+     */
+    protected Object clone() {
+        try {
+            AbstractHashedMap cloned = (AbstractHashedMap) super.clone();
+            cloned.data = new HashEntry[data.length];
+            cloned.entrySet = null;
+            cloned.keySet = null;
+            cloned.values = null;
+            cloned.modCount = 0;
+            cloned.size = 0;
+            cloned.init();
+            cloned.putAll(this);
+            return cloned;
+
+        } catch (CloneNotSupportedException ex) {
+            return null;  // should never happen
+        }
+    }
+
+    /**
+     * Compares this map with another.
+     *
+     * @param obj the object to compare to
+     * @return true if equal
+     */
+    public boolean equals(Object obj) {
+        if (obj == this) {
+            return true;
+        }
+        if (obj instanceof Map == false) {
+            return false;
+        }
+        Map map = (Map) obj;
+        if (map.size() != size()) {
+            return false;
+        }
+        MapIterator it = mapIterator();
+        try {
+            while (it.hasNext()) {
+                Object key = it.next();
+                Object value = it.getValue();
+                if (value == null) {
+                    if (map.get(key) != null || map.containsKey(key) == false) {
+                        return false;
+                    }
+                } else {
+                    if (value.equals(map.get(key)) == false) {
+                        return false;
+                    }
+                }
+            }
+        } catch (ClassCastException ignored) {
+            return false;
+        } catch (NullPointerException ignored) {
+            return false;
+        }
+        return true;
+    }
+
+    /**
+     * Gets the standard Map hashCode.
+     *
+     * @return the hash code defined in the Map interface
+     */
+    public int hashCode() {
+        int total = 0;
+        Iterator it = createEntrySetIterator();
+        while (it.hasNext()) {
+            total += it.next().hashCode();
+        }
+        return total;
+    }
+
+    /**
+     * Gets the map as a String.
+     *
+     * @return a string version of the map
+     */
+    public String toString() {
+        if (size() == 0) {
+            return "{}";
+        }
+        StringBuilder buf = new StringBuilder(32 * size());
+        buf.append('{');
+
+        MapIterator it = mapIterator();
+        boolean hasNext = it.hasNext();
+        while (hasNext) {
+            Object key = it.next();
+            Object value = it.getValue();
+            buf.append(key == this ? "(this Map)" : key).append('=').append(value == this ? "(this Map)" : value);
+
+            hasNext = it.hasNext();
+            if (hasNext) {
+                buf.append(',').append(' ');
+            }
+        }
+
+        buf.append('}');
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/collections/AbstractKeyValue.java b/src/org/jivesoftware/smack/util/collections/AbstractKeyValue.java
new file mode 100644
index 0000000..decc342
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/AbstractKeyValue.java
@@ -0,0 +1,80 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+
+/**
+ * Abstract pair class to assist with creating KeyValue and MapEntry implementations.
+ *
+ * @author James Strachan
+ * @author Michael A. Smith
+ * @author Neil O'Toole
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @since Commons Collections 3.0
+ */
+public abstract class AbstractKeyValue <K,V> implements KeyValue<K, V> {
+
+    /**
+     * The key
+     */
+    protected K key;
+    /**
+     * The value
+     */
+    protected V value;
+
+    /**
+     * Constructs a new pair with the specified key and given value.
+     *
+     * @param key   the key for the entry, may be null
+     * @param value the value for the entry, may be null
+     */
+    protected AbstractKeyValue(K key, V value) {
+        super();
+        this.key = key;
+        this.value = value;
+    }
+
+    /**
+     * Gets the key from the pair.
+     *
+     * @return the key
+     */
+    public K getKey() {
+        return key;
+    }
+
+    /**
+     * Gets the value from the pair.
+     *
+     * @return the value
+     */
+    public V getValue() {
+        return value;
+    }
+
+    /**
+     * Gets a debugging String view of the pair.
+     *
+     * @return a String view of the entry
+     */
+    public String toString() {
+        return new StringBuilder().append(getKey()).append('=').append(getValue()).toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/AbstractMapEntry.java b/src/org/jivesoftware/smack/util/collections/AbstractMapEntry.java
new file mode 100644
index 0000000..2feb308
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/AbstractMapEntry.java
@@ -0,0 +1,89 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.Map;
+
+/**
+ * Abstract Pair class to assist with creating correct Map Entry implementations.
+ *
+ * @author James Strachan
+ * @author Michael A. Smith
+ * @author Neil O'Toole
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @since Commons Collections 3.0
+ */
+public abstract class AbstractMapEntry <K,V> extends AbstractKeyValue<K, V> implements Map.Entry<K, V> {
+
+    /**
+     * Constructs a new entry with the given key and given value.
+     *
+     * @param key   the key for the entry, may be null
+     * @param value the value for the entry, may be null
+     */
+    protected AbstractMapEntry(K key, V value) {
+        super(key, value);
+    }
+
+    // Map.Entry interface
+    //-------------------------------------------------------------------------
+    /**
+     * Sets the value stored in this Map Entry.
+     * <p/>
+     * This Map Entry is not connected to a Map, so only the local data is changed.
+     *
+     * @param value the new value
+     * @return the previous value
+     */
+    public V setValue(V value) {
+        V answer = this.value;
+        this.value = value;
+        return answer;
+    }
+
+    /**
+     * Compares this Map Entry with another Map Entry.
+     * <p/>
+     * Implemented per API documentation of {@link java.util.Map.Entry#equals(Object)}
+     *
+     * @param obj the object to compare to
+     * @return true if equal key and value
+     */
+    public boolean equals(Object obj) {
+        if (obj == this) {
+            return true;
+        }
+        if (obj instanceof Map.Entry == false) {
+            return false;
+        }
+        Map.Entry other = (Map.Entry) obj;
+        return (getKey() == null ? other.getKey() == null : getKey().equals(other.getKey())) && (getValue() == null ? other.getValue() == null : getValue().equals(other.getValue()));
+    }
+
+    /**
+     * Gets a hashCode compatible with the equals method.
+     * <p/>
+     * Implemented per API documentation of {@link java.util.Map.Entry#hashCode()}
+     *
+     * @return a suitable hash code
+     */
+    public int hashCode() {
+        return (getKey() == null ? 0 : getKey().hashCode()) ^ (getValue() == null ? 0 : getValue().hashCode());
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/AbstractReferenceMap.java b/src/org/jivesoftware/smack/util/collections/AbstractReferenceMap.java
new file mode 100644
index 0000000..b57f17d
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/AbstractReferenceMap.java
@@ -0,0 +1,1025 @@
+// Converted, with some major refactors required. Not as memory-efficient as before, could use additional refactoring.
+// Perhaps use four different types of HashEntry classes for max efficiency:
+//   normal HashEntry for HARD,HARD
+//   HardRefEntry for HARD,(SOFT|WEAK)
+//   RefHardEntry for (SOFT|WEAK),HARD
+//   RefRefEntry for (SOFT|WEAK),(SOFT|WEAK)
+/*
+ *  Copyright 2002-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.lang.ref.Reference;
+import java.lang.ref.ReferenceQueue;
+import java.lang.ref.SoftReference;
+import java.lang.ref.WeakReference;
+import java.util.*;
+
+/**
+ * An abstract implementation of a hash-based map that allows the entries to
+ * be removed by the garbage collector.
+ * <p/>
+ * This class implements all the features necessary for a subclass reference
+ * hash-based map. Key-value entries are stored in instances of the
+ * <code>ReferenceEntry</code> class which can be overridden and replaced.
+ * The iterators can similarly be replaced, without the need to replace the KeySet,
+ * EntrySet and Values view classes.
+ * <p/>
+ * Overridable methods are provided to change the default hashing behaviour, and
+ * to change how entries are added to and removed from the map. Hopefully, all you
+ * need for unusual subclasses is here.
+ * <p/>
+ * When you construct an <code>AbstractReferenceMap</code>, you can specify what
+ * kind of references are used to store the map's keys and values.
+ * If non-hard references are used, then the garbage collector can remove
+ * mappings if a key or value becomes unreachable, or if the JVM's memory is
+ * running low. For information on how the different reference types behave,
+ * see {@link Reference}.
+ * <p/>
+ * Different types of references can be specified for keys and values.
+ * The keys can be configured to be weak but the values hard,
+ * in which case this class will behave like a
+ * <a href="http://java.sun.com/j2se/1.4/docs/api/java/util/WeakHashMap.html">
+ * <code>WeakHashMap</code></a>. However, you can also specify hard keys and
+ * weak values, or any other combination. The default constructor uses
+ * hard keys and soft values, providing a memory-sensitive cache.
+ * <p/>
+ * This {@link Map} implementation does <i>not</i> allow null elements.
+ * Attempting to add a null key or value to the map will raise a
+ * <code>NullPointerException</code>.
+ * <p/>
+ * All the available iterators can be reset back to the start by casting to
+ * <code>ResettableIterator</code> and calling <code>reset()</code>.
+ * <p/>
+ * This implementation is not synchronized.
+ * You can use {@link java.util.Collections#synchronizedMap} to
+ * provide synchronized access to a <code>ReferenceMap</code>.
+ *
+ * @author Paul Jack
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @see java.lang.ref.Reference
+ * @since Commons Collections 3.1 (extracted from ReferenceMap in 3.0)
+ */
+public abstract class AbstractReferenceMap <K,V> extends AbstractHashedMap<K, V> {
+
+    /**
+     * Constant indicating that hard references should be used
+     */
+    public static final int HARD = 0;
+
+    /**
+     * Constant indicating that soft references should be used
+     */
+    public static final int SOFT = 1;
+
+    /**
+     * Constant indicating that weak references should be used
+     */
+    public static final int WEAK = 2;
+
+    /**
+     * The reference type for keys.  Must be HARD, SOFT, WEAK.
+     *
+     * @serial
+     */
+    protected int keyType;
+
+    /**
+     * The reference type for values.  Must be HARD, SOFT, WEAK.
+     *
+     * @serial
+     */
+    protected int valueType;
+
+    /**
+     * Should the value be automatically purged when the associated key has been collected?
+     */
+    protected boolean purgeValues;
+
+    /**
+     * ReferenceQueue used to eliminate stale mappings.
+     * See purge.
+     */
+    private transient ReferenceQueue queue;
+
+    //-----------------------------------------------------------------------
+    /**
+     * Constructor used during deserialization.
+     */
+    protected AbstractReferenceMap() {
+        super();
+    }
+
+    /**
+     * Constructs a new empty map with the specified reference types,
+     * load factor and initial capacity.
+     *
+     * @param keyType     the type of reference to use for keys;
+     *                    must be {@link #SOFT} or {@link #WEAK}
+     * @param valueType   the type of reference to use for values;
+     *                    must be {@link #SOFT} or {@link #WEAK}
+     * @param capacity    the initial capacity for the map
+     * @param loadFactor  the load factor for the map
+     * @param purgeValues should the value be automatically purged when the
+     *                    key is garbage collected
+     */
+    protected AbstractReferenceMap(int keyType, int valueType, int capacity, float loadFactor, boolean purgeValues) {
+        super(capacity, loadFactor);
+        verify("keyType", keyType);
+        verify("valueType", valueType);
+        this.keyType = keyType;
+        this.valueType = valueType;
+        this.purgeValues = purgeValues;
+    }
+
+    /**
+     * Initialise this subclass during construction, cloning or deserialization.
+     */
+    protected void init() {
+        queue = new ReferenceQueue();
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Checks the type int is a valid value.
+     *
+     * @param name the name for error messages
+     * @param type the type value to check
+     * @throws IllegalArgumentException if the value if invalid
+     */
+    private static void verify(String name, int type) {
+        if ((type < HARD) || (type > WEAK)) {
+            throw new IllegalArgumentException(name + " must be HARD, SOFT, WEAK.");
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the size of the map.
+     *
+     * @return the size
+     */
+    public int size() {
+        purgeBeforeRead();
+        return super.size();
+    }
+
+    /**
+     * Checks whether the map is currently empty.
+     *
+     * @return true if the map is currently size zero
+     */
+    public boolean isEmpty() {
+        purgeBeforeRead();
+        return super.isEmpty();
+    }
+
+    /**
+     * Checks whether the map contains the specified key.
+     *
+     * @param key the key to search for
+     * @return true if the map contains the key
+     */
+    public boolean containsKey(Object key) {
+        purgeBeforeRead();
+        Entry entry = getEntry(key);
+        if (entry == null) {
+            return false;
+        }
+        return (entry.getValue() != null);
+    }
+
+    /**
+     * Checks whether the map contains the specified value.
+     *
+     * @param value the value to search for
+     * @return true if the map contains the value
+     */
+    public boolean containsValue(Object value) {
+        purgeBeforeRead();
+        if (value == null) {
+            return false;
+        }
+        return super.containsValue(value);
+    }
+
+    /**
+     * Gets the value mapped to the key specified.
+     *
+     * @param key the key
+     * @return the mapped value, null if no match
+     */
+    public V get(Object key) {
+        purgeBeforeRead();
+        Entry<K, V> entry = getEntry(key);
+        if (entry == null) {
+            return null;
+        }
+        return entry.getValue();
+    }
+
+
+    /**
+     * Puts a key-value mapping into this map.
+     * Neither the key nor the value may be null.
+     *
+     * @param key   the key to add, must not be null
+     * @param value the value to add, must not be null
+     * @return the value previously mapped to this key, null if none
+     * @throws NullPointerException if either the key or value is null
+     */
+    public V put(K key, V value) {
+        if (key == null) {
+            throw new NullPointerException("null keys not allowed");
+        }
+        if (value == null) {
+            throw new NullPointerException("null values not allowed");
+        }
+
+        purgeBeforeWrite();
+        return super.put(key, value);
+    }
+
+    /**
+     * Removes the specified mapping from this map.
+     *
+     * @param key the mapping to remove
+     * @return the value mapped to the removed key, null if key not in map
+     */
+    public V remove(Object key) {
+        if (key == null) {
+            return null;
+        }
+        purgeBeforeWrite();
+        return super.remove(key);
+    }
+
+    /**
+     * Clears this map.
+     */
+    public void clear() {
+        super.clear();
+        while (queue.poll() != null) {
+        } // drain the queue
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets a MapIterator over the reference map.
+     * The iterator only returns valid key/value pairs.
+     *
+     * @return a map iterator
+     */
+    public MapIterator<K, V> mapIterator() {
+        return new ReferenceMapIterator<K, V>(this);
+    }
+
+    /**
+     * Returns a set view of this map's entries.
+     * An iterator returned entry is valid until <code>next()</code> is called again.
+     * The <code>setValue()</code> method on the <code>toArray</code> entries has no effect.
+     *
+     * @return a set view of this map's entries
+     */
+    public Set<Map.Entry<K, V>> entrySet() {
+        if (entrySet == null) {
+            entrySet = new ReferenceEntrySet<K, V>(this);
+        }
+        return entrySet;
+    }
+
+    /**
+     * Returns a set view of this map's keys.
+     *
+     * @return a set view of this map's keys
+     */
+    public Set<K> keySet() {
+        if (keySet == null) {
+            keySet = new ReferenceKeySet<K, V>(this);
+        }
+        return keySet;
+    }
+
+    /**
+     * Returns a collection view of this map's values.
+     *
+     * @return a set view of this map's values
+     */
+    public Collection<V> values() {
+        if (values == null) {
+            values = new ReferenceValues<K, V>(this);
+        }
+        return values;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Purges stale mappings from this map before read operations.
+     * <p/>
+     * This implementation calls {@link #purge()} to maintain a consistent state.
+     */
+    protected void purgeBeforeRead() {
+        purge();
+    }
+
+    /**
+     * Purges stale mappings from this map before write operations.
+     * <p/>
+     * This implementation calls {@link #purge()} to maintain a consistent state.
+     */
+    protected void purgeBeforeWrite() {
+        purge();
+    }
+
+    /**
+     * Purges stale mappings from this map.
+     * <p/>
+     * Note that this method is not synchronized!  Special
+     * care must be taken if, for instance, you want stale
+     * mappings to be removed on a periodic basis by some
+     * background thread.
+     */
+    protected void purge() {
+        Reference ref = queue.poll();
+        while (ref != null) {
+            purge(ref);
+            ref = queue.poll();
+        }
+    }
+
+    /**
+     * Purges the specified reference.
+     *
+     * @param ref the reference to purge
+     */
+    protected void purge(Reference ref) {
+        // The hashCode of the reference is the hashCode of the
+        // mapping key, even if the reference refers to the
+        // mapping value...
+        int hash = ref.hashCode();
+        int index = hashIndex(hash, data.length);
+        HashEntry<K, V> previous = null;
+        HashEntry<K, V> entry = data[index];
+        while (entry != null) {
+            if (((ReferenceEntry<K, V>) entry).purge(ref)) {
+                if (previous == null) {
+                    data[index] = entry.next;
+                } else {
+                    previous.next = entry.next;
+                }
+                this.size--;
+                return;
+            }
+            previous = entry;
+            entry = entry.next;
+        }
+
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the entry mapped to the key specified.
+     *
+     * @param key the key
+     * @return the entry, null if no match
+     */
+    protected HashEntry<K, V> getEntry(Object key) {
+        if (key == null) {
+            return null;
+        } else {
+            return super.getEntry(key);
+        }
+    }
+
+    /**
+     * Gets the hash code for a MapEntry.
+     * Subclasses can override this, for example to use the identityHashCode.
+     *
+     * @param key   the key to get a hash code for, may be null
+     * @param value the value to get a hash code for, may be null
+     * @return the hash code, as per the MapEntry specification
+     */
+    protected int hashEntry(Object key, Object value) {
+        return (key == null ? 0 : key.hashCode()) ^ (value == null ? 0 : value.hashCode());
+    }
+
+    /**
+     * Compares two keys, in internal converted form, to see if they are equal.
+     * <p/>
+     * This implementation converts the key from the entry to a real reference
+     * before comparison.
+     *
+     * @param key1 the first key to compare passed in from outside
+     * @param key2 the second key extracted from the entry via <code>entry.key</code>
+     * @return true if equal
+     */
+    protected boolean isEqualKey(Object key1, Object key2) {
+        //if ((key1 == null) && (key2 != null) || (key1 != null) || (key2 == null)) {
+        //    return false;
+        //}
+        // GenericsNote: Conversion from reference handled by getKey() which replaced all .key references
+        //key2 = (keyType > HARD ? ((Reference) key2).get() : key2);
+        return (key1 == key2 || key1.equals(key2));
+    }
+
+    /**
+     * Creates a ReferenceEntry instead of a HashEntry.
+     *
+     * @param next     the next entry in sequence
+     * @param hashCode the hash code to use
+     * @param key      the key to store
+     * @param value    the value to store
+     * @return the newly created entry
+     */
+    public HashEntry<K, V> createEntry(HashEntry<K, V> next, int hashCode, K key, V value) {
+        return new ReferenceEntry<K, V>(this, (ReferenceEntry<K, V>) next, hashCode, key, value);
+    }
+
+    /**
+     * Creates an entry set iterator.
+     *
+     * @return the entrySet iterator
+     */
+    protected Iterator<Map.Entry<K, V>> createEntrySetIterator() {
+        return new ReferenceEntrySetIterator<K, V>(this);
+    }
+
+    /**
+     * Creates an key set iterator.
+     *
+     * @return the keySet iterator
+     */
+    protected Iterator<K> createKeySetIterator() {
+        return new ReferenceKeySetIterator<K, V>(this);
+    }
+
+    /**
+     * Creates an values iterator.
+     *
+     * @return the values iterator
+     */
+    protected Iterator<V> createValuesIterator() {
+        return new ReferenceValuesIterator<K, V>(this);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * EntrySet implementation.
+     */
+    static class ReferenceEntrySet <K,V> extends EntrySet<K, V> {
+
+        protected ReferenceEntrySet(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public Object[] toArray() {
+            return toArray(new Object[0]);
+        }
+
+        public <T> T[] toArray(T[] arr) {
+            // special implementation to handle disappearing entries
+            ArrayList<Map.Entry<K, V>> list = new ArrayList<Map.Entry<K, V>>();
+            Iterator<Map.Entry<K, V>> iterator = iterator();
+            while (iterator.hasNext()) {
+                Map.Entry<K, V> e = iterator.next();
+                list.add(new DefaultMapEntry<K, V>(e.getKey(), e.getValue()));
+            }
+            return list.toArray(arr);
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * KeySet implementation.
+     */
+    static class ReferenceKeySet <K,V> extends KeySet<K, V> {
+
+        protected ReferenceKeySet(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public Object[] toArray() {
+            return toArray(new Object[0]);
+        }
+
+        public <T> T[] toArray(T[] arr) {
+            // special implementation to handle disappearing keys
+            List<K> list = new ArrayList<K>(parent.size());
+            for (Iterator<K> it = iterator(); it.hasNext();) {
+                list.add(it.next());
+            }
+            return list.toArray(arr);
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Values implementation.
+     */
+    static class ReferenceValues <K,V> extends Values<K, V> {
+
+        protected ReferenceValues(AbstractHashedMap<K, V> parent) {
+            super(parent);
+        }
+
+        public Object[] toArray() {
+            return toArray(new Object[0]);
+        }
+
+        public <T> T[] toArray(T[] arr) {
+            // special implementation to handle disappearing values
+            List<V> list = new ArrayList<V>(parent.size());
+            for (Iterator<V> it = iterator(); it.hasNext();) {
+                list.add(it.next());
+            }
+            return list.toArray(arr);
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * A MapEntry implementation for the map.
+     * <p/>
+     * If getKey() or getValue() returns null, it means
+     * the mapping is stale and should be removed.
+     *
+     * @since Commons Collections 3.1
+     */
+    protected static class ReferenceEntry <K,V> extends HashEntry<K, V> {
+        /**
+         * The parent map
+         */
+        protected final AbstractReferenceMap<K, V> parent;
+
+        protected Reference<K> refKey;
+        protected Reference<V> refValue;
+
+        /**
+         * Creates a new entry object for the ReferenceMap.
+         *
+         * @param parent   the parent map
+         * @param next     the next entry in the hash bucket
+         * @param hashCode the hash code of the key
+         * @param key      the key
+         * @param value    the value
+         */
+        public ReferenceEntry(AbstractReferenceMap<K, V> parent, ReferenceEntry<K, V> next, int hashCode, K key, V value) {
+            super(next, hashCode, null, null);
+            this.parent = parent;
+            if (parent.keyType != HARD) {
+                refKey = toReference(parent.keyType, key, hashCode);
+            } else {
+                this.setKey(key);
+            }
+            if (parent.valueType != HARD) {
+                refValue = toReference(parent.valueType, value, hashCode); // the key hashCode is passed in deliberately
+            } else {
+                this.setValue(value);
+            }
+        }
+
+        /**
+         * Gets the key from the entry.
+         * This method dereferences weak and soft keys and thus may return null.
+         *
+         * @return the key, which may be null if it was garbage collected
+         */
+        public K getKey() {
+            return (parent.keyType > HARD) ? refKey.get() : super.getKey();
+        }
+
+        /**
+         * Gets the value from the entry.
+         * This method dereferences weak and soft value and thus may return null.
+         *
+         * @return the value, which may be null if it was garbage collected
+         */
+        public V getValue() {
+            return (parent.valueType > HARD) ? refValue.get() : super.getValue();
+        }
+
+        /**
+         * Sets the value of the entry.
+         *
+         * @param obj the object to store
+         * @return the previous value
+         */
+        public V setValue(V obj) {
+            V old = getValue();
+            if (parent.valueType > HARD) {
+                refValue.clear();
+                refValue = toReference(parent.valueType, obj, hashCode);
+            } else {
+                super.setValue(obj);
+            }
+            return old;
+        }
+
+        /**
+         * Compares this map entry to another.
+         * <p/>
+         * This implementation uses <code>isEqualKey</code> and
+         * <code>isEqualValue</code> on the main map for comparison.
+         *
+         * @param obj the other map entry to compare to
+         * @return true if equal, false if not
+         */
+        public boolean equals(Object obj) {
+            if (obj == this) {
+                return true;
+            }
+            if (obj instanceof Map.Entry == false) {
+                return false;
+            }
+
+            Map.Entry entry = (Map.Entry) obj;
+            Object entryKey = entry.getKey();  // convert to hard reference
+            Object entryValue = entry.getValue();  // convert to hard reference
+            if ((entryKey == null) || (entryValue == null)) {
+                return false;
+            }
+            // compare using map methods, aiding identity subclass
+            // note that key is direct access and value is via method
+            return parent.isEqualKey(entryKey, getKey()) && parent.isEqualValue(entryValue, getValue());
+        }
+
+        /**
+         * Gets the hashcode of the entry using temporary hard references.
+         * <p/>
+         * This implementation uses <code>hashEntry</code> on the main map.
+         *
+         * @return the hashcode of the entry
+         */
+        public int hashCode() {
+            return parent.hashEntry(getKey(), getValue());
+        }
+
+        /**
+         * Constructs a reference of the given type to the given referent.
+         * The reference is registered with the queue for later purging.
+         *
+         * @param type     HARD, SOFT or WEAK
+         * @param referent the object to refer to
+         * @param hash     the hash code of the <i>key</i> of the mapping;
+         *                 this number might be different from referent.hashCode() if
+         *                 the referent represents a value and not a key
+         */
+        protected <T> Reference<T> toReference(int type, T referent, int hash) {
+            switch (type) {
+                case SOFT:
+                    return new SoftRef<T>(hash, referent, parent.queue);
+                case WEAK:
+                    return new WeakRef<T>(hash, referent, parent.queue);
+                default:
+                    throw new Error("Attempt to create hard reference in ReferenceMap!");
+            }
+        }
+
+        /**
+         * Purges the specified reference
+         *
+         * @param ref the reference to purge
+         * @return true or false
+         */
+        boolean purge(Reference ref) {
+            boolean r = (parent.keyType > HARD) && (refKey == ref);
+            r = r || ((parent.valueType > HARD) && (refValue == ref));
+            if (r) {
+                if (parent.keyType > HARD) {
+                    refKey.clear();
+                }
+                if (parent.valueType > HARD) {
+                    refValue.clear();
+                } else if (parent.purgeValues) {
+                    setValue(null);
+                }
+            }
+            return r;
+        }
+
+        /**
+         * Gets the next entry in the bucket.
+         *
+         * @return the next entry in the bucket
+         */
+        protected ReferenceEntry<K, V> next() {
+            return (ReferenceEntry<K, V>) next;
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * The EntrySet iterator.
+     */
+    static class ReferenceIteratorBase <K,V> {
+        /**
+         * The parent map
+         */
+        final AbstractReferenceMap<K, V> parent;
+
+        // These fields keep track of where we are in the table.
+        int index;
+        ReferenceEntry<K, V> entry;
+        ReferenceEntry<K, V> previous;
+
+        // These Object fields provide hard references to the
+        // current and next entry; this assures that if hasNext()
+        // returns true, next() will actually return a valid element.
+        K nextKey;
+        V nextValue;
+        K currentKey;
+        V currentValue;
+
+        int expectedModCount;
+
+        public ReferenceIteratorBase(AbstractReferenceMap<K, V> parent) {
+            super();
+            this.parent = parent;
+            index = (parent.size() != 0 ? parent.data.length : 0);
+            // have to do this here!  size() invocation above
+            // may have altered the modCount.
+            expectedModCount = parent.modCount;
+        }
+
+        public boolean hasNext() {
+            checkMod();
+            while (nextNull()) {
+                ReferenceEntry<K, V> e = entry;
+                int i = index;
+                while ((e == null) && (i > 0)) {
+                    i--;
+                    e = (ReferenceEntry<K, V>) parent.data[i];
+                }
+                entry = e;
+                index = i;
+                if (e == null) {
+                    currentKey = null;
+                    currentValue = null;
+                    return false;
+                }
+                nextKey = e.getKey();
+                nextValue = e.getValue();
+                if (nextNull()) {
+                    entry = entry.next();
+                }
+            }
+            return true;
+        }
+
+        private void checkMod() {
+            if (parent.modCount != expectedModCount) {
+                throw new ConcurrentModificationException();
+            }
+        }
+
+        private boolean nextNull() {
+            return (nextKey == null) || (nextValue == null);
+        }
+
+        protected ReferenceEntry<K, V> nextEntry() {
+            checkMod();
+            if (nextNull() && !hasNext()) {
+                throw new NoSuchElementException();
+            }
+            previous = entry;
+            entry = entry.next();
+            currentKey = nextKey;
+            currentValue = nextValue;
+            nextKey = null;
+            nextValue = null;
+            return previous;
+        }
+
+        protected ReferenceEntry<K, V> currentEntry() {
+            checkMod();
+            return previous;
+        }
+
+        public ReferenceEntry<K, V> superNext() {
+            return nextEntry();
+        }
+
+        public void remove() {
+            checkMod();
+            if (previous == null) {
+                throw new IllegalStateException();
+            }
+            parent.remove(currentKey);
+            previous = null;
+            currentKey = null;
+            currentValue = null;
+            expectedModCount = parent.modCount;
+        }
+    }
+
+    /**
+     * The EntrySet iterator.
+     */
+    static class ReferenceEntrySetIterator <K,V> extends ReferenceIteratorBase<K, V> implements Iterator<Map.Entry<K, V>> {
+
+        public ReferenceEntrySetIterator(AbstractReferenceMap<K, V> abstractReferenceMap) {
+            super(abstractReferenceMap);
+        }
+
+        public ReferenceEntry<K, V> next() {
+            return superNext();
+        }
+
+    }
+
+    /**
+     * The keySet iterator.
+     */
+    static class ReferenceKeySetIterator <K,V> extends ReferenceIteratorBase<K, V> implements Iterator<K> {
+
+        ReferenceKeySetIterator(AbstractReferenceMap<K, V> parent) {
+            super(parent);
+        }
+
+        public K next() {
+            return nextEntry().getKey();
+        }
+    }
+
+    /**
+     * The values iterator.
+     */
+    static class ReferenceValuesIterator <K,V> extends ReferenceIteratorBase<K, V> implements Iterator<V> {
+
+        ReferenceValuesIterator(AbstractReferenceMap<K, V> parent) {
+            super(parent);
+        }
+
+        public V next() {
+            return nextEntry().getValue();
+        }
+    }
+
+    /**
+     * The MapIterator implementation.
+     */
+    static class ReferenceMapIterator <K,V> extends ReferenceIteratorBase<K, V> implements MapIterator<K, V> {
+
+        protected ReferenceMapIterator(AbstractReferenceMap<K, V> parent) {
+            super(parent);
+        }
+
+        public K next() {
+            return nextEntry().getKey();
+        }
+
+        public K getKey() {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.GETKEY_INVALID);
+            }
+            return current.getKey();
+        }
+
+        public V getValue() {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.GETVALUE_INVALID);
+            }
+            return current.getValue();
+        }
+
+        public V setValue(V value) {
+            HashEntry<K, V> current = currentEntry();
+            if (current == null) {
+                throw new IllegalStateException(AbstractHashedMap.SETVALUE_INVALID);
+            }
+            return current.setValue(value);
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    // These two classes store the hashCode of the key of
+    // of the mapping, so that after they're dequeued a quick
+    // lookup of the bucket in the table can occur.
+
+    /**
+     * A soft reference holder.
+     */
+    static class SoftRef <T> extends SoftReference<T> {
+        /**
+         * the hashCode of the key (even if the reference points to a value)
+         */
+        private int hash;
+
+        public SoftRef(int hash, T r, ReferenceQueue q) {
+            super(r, q);
+            this.hash = hash;
+        }
+
+        public int hashCode() {
+            return hash;
+        }
+    }
+
+    /**
+     * A weak reference holder.
+     */
+    static class WeakRef <T> extends WeakReference<T> {
+        /**
+         * the hashCode of the key (even if the reference points to a value)
+         */
+        private int hash;
+
+        public WeakRef(int hash, T r, ReferenceQueue q) {
+            super(r, q);
+            this.hash = hash;
+        }
+
+        public int hashCode() {
+            return hash;
+        }
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Replaces the superclass method to store the state of this class.
+     * <p/>
+     * Serialization is not one of the JDK's nicest topics. Normal serialization will
+     * initialise the superclass before the subclass. Sometimes however, this isn't
+     * what you want, as in this case the <code>put()</code> method on read can be
+     * affected by subclass state.
+     * <p/>
+     * The solution adopted here is to serialize the state data of this class in
+     * this protected method. This method must be called by the
+     * <code>writeObject()</code> of the first serializable subclass.
+     * <p/>
+     * Subclasses may override if they have a specific field that must be present
+     * on read before this implementation will work. Generally, the read determines
+     * what must be serialized here, if anything.
+     *
+     * @param out the output stream
+     */
+    protected void doWriteObject(ObjectOutputStream out) throws IOException {
+        out.writeInt(keyType);
+        out.writeInt(valueType);
+        out.writeBoolean(purgeValues);
+        out.writeFloat(loadFactor);
+        out.writeInt(data.length);
+        for (MapIterator it = mapIterator(); it.hasNext();) {
+            out.writeObject(it.next());
+            out.writeObject(it.getValue());
+        }
+        out.writeObject(null);  // null terminate map
+        // do not call super.doWriteObject() as code there doesn't work for reference map
+    }
+
+    /**
+     * Replaces the superclassm method to read the state of this class.
+     * <p/>
+     * Serialization is not one of the JDK's nicest topics. Normal serialization will
+     * initialise the superclass before the subclass. Sometimes however, this isn't
+     * what you want, as in this case the <code>put()</code> method on read can be
+     * affected by subclass state.
+     * <p/>
+     * The solution adopted here is to deserialize the state data of this class in
+     * this protected method. This method must be called by the
+     * <code>readObject()</code> of the first serializable subclass.
+     * <p/>
+     * Subclasses may override if the subclass has a specific field that must be present
+     * before <code>put()</code> or <code>calculateThreshold()</code> will work correctly.
+     *
+     * @param in the input stream
+     */
+    protected void doReadObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
+        this.keyType = in.readInt();
+        this.valueType = in.readInt();
+        this.purgeValues = in.readBoolean();
+        this.loadFactor = in.readFloat();
+        int capacity = in.readInt();
+        init();
+        data = new HashEntry[capacity];
+        while (true) {
+            K key = (K) in.readObject();
+            if (key == null) {
+                break;
+            }
+            V value = (V) in.readObject();
+            put(key, value);
+        }
+        threshold = calculateThreshold(data.length, loadFactor);
+        // do not call super.doReadObject() as code there doesn't work for reference map
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/DefaultMapEntry.java b/src/org/jivesoftware/smack/util/collections/DefaultMapEntry.java
new file mode 100644
index 0000000..ef752d0
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/DefaultMapEntry.java
@@ -0,0 +1,65 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2001-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+
+import java.util.Map;
+
+/**
+ * A restricted implementation of {@link java.util.Map.Entry} that prevents
+ * the MapEntry contract from being broken.
+ *
+ * @author James Strachan
+ * @author Michael A. Smith
+ * @author Neil O'Toole
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @since Commons Collections 3.0
+ */
+public final class DefaultMapEntry <K,V> extends AbstractMapEntry<K, V> {
+
+    /**
+     * Constructs a new entry with the specified key and given value.
+     *
+     * @param key   the key for the entry, may be null
+     * @param value the value for the entry, may be null
+     */
+    public DefaultMapEntry(final K key, final V value) {
+        super(key, value);
+    }
+
+    /**
+     * Constructs a new entry from the specified KeyValue.
+     *
+     * @param pair the pair to copy, must not be null
+     * @throws NullPointerException if the entry is null
+     */
+    public DefaultMapEntry(final KeyValue<K, V> pair) {
+        super(pair.getKey(), pair.getValue());
+    }
+
+    /**
+     * Constructs a new entry from the specified MapEntry.
+     *
+     * @param entry the entry to copy, must not be null
+     * @throws NullPointerException if the entry is null
+     */
+    public DefaultMapEntry(final Map.Entry<K, V> entry) {
+        super(entry.getKey(), entry.getValue());
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/EmptyIterator.java b/src/org/jivesoftware/smack/util/collections/EmptyIterator.java
new file mode 100644
index 0000000..6a8707f
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/EmptyIterator.java
@@ -0,0 +1,58 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.Iterator;
+
+/**
+ * Provides an implementation of an empty iterator.
+ * <p/>
+ * This class provides an implementation of an empty iterator.
+ * This class provides for binary compatability between Commons Collections
+ * 2.1.1 and 3.1 due to issues with <code>IteratorUtils</code>.
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:24 $
+ * @since Commons Collections 2.1.1 and 3.1
+ */
+public class EmptyIterator <E> extends AbstractEmptyIterator<E> implements ResettableIterator<E> {
+
+    /**
+     * Singleton instance of the iterator.
+     *
+     * @since Commons Collections 3.1
+     */
+    public static final ResettableIterator RESETTABLE_INSTANCE = new EmptyIterator();
+    /**
+     * Singleton instance of the iterator.
+     *
+     * @since Commons Collections 2.1.1 and 3.1
+     */
+    public static final Iterator INSTANCE = RESETTABLE_INSTANCE;
+
+	public static <T> Iterator<T> getInstance() {
+		return INSTANCE;
+	}
+	
+    /**
+     * Constructor.
+     */
+    protected EmptyIterator() {
+        super();
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/EmptyMapIterator.java b/src/org/jivesoftware/smack/util/collections/EmptyMapIterator.java
new file mode 100644
index 0000000..013f5ed
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/EmptyMapIterator.java
@@ -0,0 +1,42 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+/**
+ * Provides an implementation of an empty map iterator.
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:24 $
+ * @since Commons Collections 3.1
+ */
+public class EmptyMapIterator extends AbstractEmptyIterator implements MapIterator, ResettableIterator {
+
+    /**
+     * Singleton instance of the iterator.
+     *
+     * @since Commons Collections 3.1
+     */
+    public static final MapIterator INSTANCE = new EmptyMapIterator();
+
+    /**
+     * Constructor.
+     */
+    protected EmptyMapIterator() {
+        super();
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/IterableMap.java b/src/org/jivesoftware/smack/util/collections/IterableMap.java
new file mode 100644
index 0000000..251b587
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/IterableMap.java
@@ -0,0 +1,61 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.Map;
+
+/**
+ * Defines a map that can be iterated directly without needing to create an entry set.
+ * <p/>
+ * A map iterator is an efficient way of iterating over maps.
+ * There is no need to access the entry set or cast to Map Entry objects.
+ * <pre>
+ * IterableMap map = new HashedMap();
+ * MapIterator it = map.mapIterator();
+ * while (it.hasNext()) {
+ *   Object key = it.next();
+ *   Object value = it.getValue();
+ *   it.setValue("newValue");
+ * }
+ * </pre>
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:19 $
+ * @since Commons Collections 3.0
+ */
+public interface IterableMap <K,V> extends Map<K, V> {
+
+    /**
+     * Obtains a <code>MapIterator</code> over the map.
+     * <p/>
+     * A map iterator is an efficient way of iterating over maps.
+     * There is no need to access the entry set or cast to Map Entry objects.
+     * <pre>
+     * IterableMap map = new HashedMap();
+     * MapIterator it = map.mapIterator();
+     * while (it.hasNext()) {
+     *   Object key = it.next();
+     *   Object value = it.getValue();
+     *   it.setValue("newValue");
+     * }
+     * </pre>
+     *
+     * @return a map iterator
+     */
+    MapIterator<K, V> mapIterator();
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/KeyValue.java b/src/org/jivesoftware/smack/util/collections/KeyValue.java
new file mode 100644
index 0000000..c73621d
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/KeyValue.java
@@ -0,0 +1,46 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+/**
+ * Defines a simple key value pair.
+ * <p/>
+ * A Map Entry has considerable additional semantics over and above a simple
+ * key-value pair. This interface defines the minimum key value, with just the
+ * two get methods.
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:19 $
+ * @since Commons Collections 3.0
+ */
+public interface KeyValue <K,V> {
+
+    /**
+     * Gets the key from the pair.
+     *
+     * @return the key
+     */
+    K getKey();
+
+    /**
+     * Gets the value from the pair.
+     *
+     * @return the value
+     */
+    V getValue();
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/MapIterator.java b/src/org/jivesoftware/smack/util/collections/MapIterator.java
new file mode 100644
index 0000000..fe2398c
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/MapIterator.java
@@ -0,0 +1,109 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.Iterator;
+
+/**
+ * Defines an iterator that operates over a <code>Map</code>.
+ * <p/>
+ * This iterator is a special version designed for maps. It can be more
+ * efficient to use this rather than an entry set iterator where the option
+ * is available, and it is certainly more convenient.
+ * <p/>
+ * A map that provides this interface may not hold the data internally using
+ * Map Entry objects, thus this interface can avoid lots of object creation.
+ * <p/>
+ * In use, this iterator iterates through the keys in the map. After each call
+ * to <code>next()</code>, the <code>getValue()</code> method provides direct
+ * access to the value. The value can also be set using <code>setValue()</code>.
+ * <pre>
+ * MapIterator it = map.mapIterator();
+ * while (it.hasNext()) {
+ *   Object key = it.next();
+ *   Object value = it.getValue();
+ *   it.setValue(newValue);
+ * }
+ * </pre>
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:19 $
+ * @since Commons Collections 3.0
+ */
+public interface MapIterator <K,V> extends Iterator<K> {
+
+    /**
+     * Checks to see if there are more entries still to be iterated.
+     *
+     * @return <code>true</code> if the iterator has more elements
+     */
+    boolean hasNext();
+
+    /**
+     * Gets the next <em>key</em> from the <code>Map</code>.
+     *
+     * @return the next key in the iteration
+     * @throws java.util.NoSuchElementException
+     *          if the iteration is finished
+     */
+    K next();
+
+    //-----------------------------------------------------------------------
+    /**
+     * Gets the current key, which is the key returned by the last call
+     * to <code>next()</code>.
+     *
+     * @return the current key
+     * @throws IllegalStateException if <code>next()</code> has not yet been called
+     */
+    K getKey();
+
+    /**
+     * Gets the current value, which is the value associated with the last key
+     * returned by <code>next()</code>.
+     *
+     * @return the current value
+     * @throws IllegalStateException if <code>next()</code> has not yet been called
+     */
+    V getValue();
+
+    //-----------------------------------------------------------------------
+    /**
+     * Removes the last returned key from the underlying <code>Map</code> (optional operation).
+     * <p/>
+     * This method can be called once per call to <code>next()</code>.
+     *
+     * @throws UnsupportedOperationException if remove is not supported by the map
+     * @throws IllegalStateException         if <code>next()</code> has not yet been called
+     * @throws IllegalStateException         if <code>remove()</code> has already been called
+     *                                       since the last call to <code>next()</code>
+     */
+    void remove();
+
+    /**
+     * Sets the value associated with the current key (optional operation).
+     *
+     * @param value the new value
+     * @return the previous value
+     * @throws UnsupportedOperationException if setValue is not supported by the map
+     * @throws IllegalStateException         if <code>next()</code> has not yet been called
+     * @throws IllegalStateException         if <code>remove()</code> has been called since the
+     *                                       last call to <code>next()</code>
+     */
+    V setValue(V value);
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/ReferenceMap.java b/src/org/jivesoftware/smack/util/collections/ReferenceMap.java
new file mode 100644
index 0000000..f30954d
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/ReferenceMap.java
@@ -0,0 +1,161 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2002-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+
+/**
+ * A <code>Map</code> implementation that allows mappings to be
+ * removed by the garbage collector.
+ * <p/>
+ * When you construct a <code>ReferenceMap</code>, you can specify what kind
+ * of references are used to store the map's keys and values.
+ * If non-hard references are used, then the garbage collector can remove
+ * mappings if a key or value becomes unreachable, or if the JVM's memory is
+ * running low. For information on how the different reference types behave,
+ * see {@link java.lang.ref.Reference}.
+ * <p/>
+ * Different types of references can be specified for keys and values.
+ * The keys can be configured to be weak but the values hard,
+ * in which case this class will behave like a
+ * <a href="http://java.sun.com/j2se/1.4/docs/api/java/util/WeakHashMap.html">
+ * <code>WeakHashMap</code></a>. However, you can also specify hard keys and
+ * weak values, or any other combination. The default constructor uses
+ * hard keys and soft values, providing a memory-sensitive cache.
+ * <p/>
+ * This map is similar to ReferenceIdentityMap.
+ * It differs in that keys and values in this class are compared using <code>equals()</code>.
+ * <p/>
+ * This {@link java.util.Map} implementation does <i>not</i> allow null elements.
+ * Attempting to add a null key or value to the map will raise a <code>NullPointerException</code>.
+ * <p/>
+ * This implementation is not synchronized.
+ * You can use {@link java.util.Collections#synchronizedMap} to
+ * provide synchronized access to a <code>ReferenceMap</code>.
+ * Remember that synchronization will not stop the garbage collecter removing entries.
+ * <p/>
+ * All the available iterators can be reset back to the start by casting to
+ * <code>ResettableIterator</code> and calling <code>reset()</code>.
+ * <p/>
+ * NOTE: As from Commons Collections 3.1 this map extends <code>AbstractReferenceMap</code>
+ * (previously it extended AbstractMap). As a result, the implementation is now
+ * extensible and provides a <code>MapIterator</code>.
+ *
+ * @author Paul Jack
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:32 $
+ * @see java.lang.ref.Reference
+ * @since Commons Collections 3.0 (previously in main package v2.1)
+ */
+public class ReferenceMap <K,V> extends AbstractReferenceMap<K, V> implements Serializable {
+
+    /**
+     * Serialization version
+     */
+    private static final long serialVersionUID = 1555089888138299607L;
+
+    /**
+     * Constructs a new <code>ReferenceMap</code> that will
+     * use hard references to keys and soft references to values.
+     */
+    public ReferenceMap() {
+        super(HARD, SOFT, DEFAULT_CAPACITY, DEFAULT_LOAD_FACTOR, false);
+    }
+
+    /**
+     * Constructs a new <code>ReferenceMap</code> that will
+     * use the specified types of references.
+     *
+     * @param keyType   the type of reference to use for keys;
+     *                  must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param valueType the type of reference to use for values;
+     *                  must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     */
+    public ReferenceMap(int keyType, int valueType) {
+        super(keyType, valueType, DEFAULT_CAPACITY, DEFAULT_LOAD_FACTOR, false);
+    }
+
+    /**
+     * Constructs a new <code>ReferenceMap</code> that will
+     * use the specified types of references.
+     *
+     * @param keyType     the type of reference to use for keys;
+     *                    must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param valueType   the type of reference to use for values;
+     *                    must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param purgeValues should the value be automatically purged when the
+     *                    key is garbage collected
+     */
+    public ReferenceMap(int keyType, int valueType, boolean purgeValues) {
+        super(keyType, valueType, DEFAULT_CAPACITY, DEFAULT_LOAD_FACTOR, purgeValues);
+    }
+
+    /**
+     * Constructs a new <code>ReferenceMap</code> with the
+     * specified reference types, load factor and initial
+     * capacity.
+     *
+     * @param keyType    the type of reference to use for keys;
+     *                   must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param valueType  the type of reference to use for values;
+     *                   must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param capacity   the initial capacity for the map
+     * @param loadFactor the load factor for the map
+     */
+    public ReferenceMap(int keyType, int valueType, int capacity, float loadFactor) {
+        super(keyType, valueType, capacity, loadFactor, false);
+    }
+
+    /**
+     * Constructs a new <code>ReferenceMap</code> with the
+     * specified reference types, load factor and initial
+     * capacity.
+     *
+     * @param keyType     the type of reference to use for keys;
+     *                    must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param valueType   the type of reference to use for values;
+     *                    must be {@link #HARD}, {@link #SOFT}, {@link #WEAK}
+     * @param capacity    the initial capacity for the map
+     * @param loadFactor  the load factor for the map
+     * @param purgeValues should the value be automatically purged when the
+     *                    key is garbage collected
+     */
+    public ReferenceMap(int keyType, int valueType, int capacity, float loadFactor, boolean purgeValues) {
+        super(keyType, valueType, capacity, loadFactor, purgeValues);
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Write the map out using a custom routine.
+     */
+    private void writeObject(ObjectOutputStream out) throws IOException {
+        out.defaultWriteObject();
+        doWriteObject(out);
+    }
+
+    /**
+     * Read the map in using a custom routine.
+     */
+    private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
+        in.defaultReadObject();
+        doReadObject(in);
+    }
+
+}
diff --git a/src/org/jivesoftware/smack/util/collections/ResettableIterator.java b/src/org/jivesoftware/smack/util/collections/ResettableIterator.java
new file mode 100644
index 0000000..cf814f7
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/collections/ResettableIterator.java
@@ -0,0 +1,38 @@
+// GenericsNote: Converted.
+/*
+ *  Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.jivesoftware.smack.util.collections;
+
+import java.util.Iterator;
+
+/**
+ * Defines an iterator that can be reset back to an initial state.
+ * <p/>
+ * This interface allows an iterator to be repeatedly reused.
+ *
+ * @author Matt Hall, John Watkinson, Stephen Colebourne
+ * @version $Revision: 1.1 $ $Date: 2005/10/11 17:05:19 $
+ * @since Commons Collections 3.0
+ */
+public interface ResettableIterator <E> extends Iterator<E> {
+
+    /**
+     * Resets the iterator back to the position at which the iterator
+     * was created.
+     */
+    public void reset();
+
+}
diff --git a/src/org/jivesoftware/smack/util/dns/DNSJavaResolver.java b/src/org/jivesoftware/smack/util/dns/DNSJavaResolver.java
new file mode 100644
index 0000000..dd93fd3
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/dns/DNSJavaResolver.java
@@ -0,0 +1,73 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util.dns;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.xbill.DNS.Lookup;
+import org.xbill.DNS.Record;
+import org.xbill.DNS.Type;
+
+/**
+ * This implementation uses the <a href="http://www.dnsjava.org/">dnsjava</a> implementation for resolving DNS addresses.
+ *
+ */
+public class DNSJavaResolver implements DNSResolver {
+    
+    private static DNSJavaResolver instance = new DNSJavaResolver();
+    
+    private DNSJavaResolver() {
+        
+    }
+    
+    public static DNSResolver getInstance() {
+        return instance;
+    }
+
+    @Override
+    public List<SRVRecord> lookupSRVRecords(String name) {
+        List<SRVRecord> res = new ArrayList<SRVRecord>();
+
+        try {
+            Lookup lookup = new Lookup(name, Type.SRV);
+            Record recs[] = lookup.run();
+            if (recs == null)
+                return res;
+
+            for (Record record : recs) {
+                org.xbill.DNS.SRVRecord srvRecord = (org.xbill.DNS.SRVRecord) record;
+                if (srvRecord != null && srvRecord.getTarget() != null) {
+                    String host = srvRecord.getTarget().toString();
+                    int port = srvRecord.getPort();
+                    int priority = srvRecord.getPriority();
+                    int weight = srvRecord.getWeight();
+
+                    SRVRecord r;
+                    try {
+                        r = new SRVRecord(host, port, priority, weight);
+                    } catch (Exception e) {
+                        continue;
+                    }
+                    res.add(r);
+                }
+            }
+
+        } catch (Exception e) {
+        }
+        return res;
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/dns/DNSResolver.java b/src/org/jivesoftware/smack/util/dns/DNSResolver.java
new file mode 100644
index 0000000..86f037b
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/dns/DNSResolver.java
@@ -0,0 +1,33 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util.dns;
+
+import java.util.List;
+
+/**
+ * Implementations of this interface define a class that is capable of resolving DNS addresses.
+ *
+ */
+public interface DNSResolver {
+
+    /**
+     * Gets a list of service records for the specified service.
+     * @param name The symbolic name of the service.
+     * @return The list of SRV records mapped to the service name.
+     */
+    List<SRVRecord> lookupSRVRecords(String name);
+
+}
diff --git a/src/org/jivesoftware/smack/util/dns/HostAddress.java b/src/org/jivesoftware/smack/util/dns/HostAddress.java
new file mode 100644
index 0000000..eb8b07a
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/dns/HostAddress.java
@@ -0,0 +1,109 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util.dns;
+
+public class HostAddress {
+    private String fqdn;
+    private int port;
+    private Exception exception;
+
+    /**
+     * Creates a new HostAddress with the given FQDN. The port will be set to the default XMPP client port: 5222
+     * 
+     * @param fqdn Fully qualified domain name.
+     * @throws IllegalArgumentException If the fqdn is null.
+     */
+    public HostAddress(String fqdn) {
+        if (fqdn == null)
+            throw new IllegalArgumentException("FQDN is null");
+        if (fqdn.charAt(fqdn.length() - 1) == '.') {
+            this.fqdn = fqdn.substring(0, fqdn.length() - 1);
+        }
+        else {
+            this.fqdn = fqdn;
+        }
+        // Set port to the default port for XMPP client communication
+        this.port = 5222;
+    }
+
+    /**
+     * Creates a new HostAddress with the given FQDN. The port will be set to the default XMPP client port: 5222
+     * 
+     * @param fqdn Fully qualified domain name.
+     * @param port The port to connect on.
+     * @throws IllegalArgumentException If the fqdn is null or port is out of valid range (0 - 65535).
+     */
+    public HostAddress(String fqdn, int port) {
+        this(fqdn);
+        if (port < 0 || port > 65535)
+            throw new IllegalArgumentException(
+                    "DNS SRV records weight must be a 16-bit unsiged integer (i.e. between 0-65535. Port was: " + port);
+
+        this.port = port;
+    }
+
+    public String getFQDN() {
+        return fqdn;
+    }
+
+    public int getPort() {
+        return port;
+    }
+
+    public void setException(Exception e) {
+        this.exception = e;
+    }
+
+    @Override
+    public String toString() {
+        return fqdn + ":" + port;
+    }
+
+    @Override
+    public boolean equals(Object o) {
+        if (this == o) {
+            return true;
+        }
+        if (!(o instanceof HostAddress)) {
+            return false;
+        }
+
+        final HostAddress address = (HostAddress) o;
+
+        if (!fqdn.equals(address.fqdn)) {
+            return false;
+        }
+        return port == address.port;
+    }
+
+    @Override
+    public int hashCode() {
+        int result = 1;
+        result = 37 * result + fqdn.hashCode();
+        return result * 37 + port;
+    }
+
+    public String getErrorMessage() {
+        String error;
+        if (exception == null) {
+            error = "No error logged";
+        }
+        else {
+            error = exception.getMessage();
+        }
+        return toString() + " Exception: " + error;
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/dns/SRVRecord.java b/src/org/jivesoftware/smack/util/dns/SRVRecord.java
new file mode 100644
index 0000000..457e40e
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/dns/SRVRecord.java
@@ -0,0 +1,79 @@
+/**
+ * Copyright 2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smack.util.dns;
+
+/**
+ * @see <a href="http://tools.ietf.org/html/rfc2782>RFC 2782: A DNS RR for specifying the location of services (DNS
+ * SRV)<a>
+ * @author Florian Schmaus
+ * 
+ */
+public class SRVRecord extends HostAddress implements Comparable<SRVRecord> {
+    
+    private int weight;
+    private int priority;
+    
+    /**
+     * Create a new SRVRecord
+     * 
+     * @param fqdn Fully qualified domain name
+     * @param port The connection port
+     * @param priority Priority of the target host
+     * @param weight Relative weight for records with same priority
+     * @throws IllegalArgumentException fqdn is null or any other field is not in valid range (0-65535).
+     */
+    public SRVRecord(String fqdn, int port, int priority, int weight) {
+        super(fqdn, port);
+        if (weight < 0 || weight > 65535)
+            throw new IllegalArgumentException(
+                    "DNS SRV records weight must be a 16-bit unsiged integer (i.e. between 0-65535. Weight was: "
+                            + weight);
+
+        if (priority < 0 || priority > 65535)
+            throw new IllegalArgumentException(
+                    "DNS SRV records priority must be a 16-bit unsiged integer (i.e. between 0-65535. Priority was: "
+                            + priority);
+
+        this.priority = priority;
+        this.weight = weight;
+
+    }
+    
+    public int getPriority() {
+        return priority;
+    }
+    
+    public int getWeight() {
+        return weight;
+    }
+
+    @Override
+    public int compareTo(SRVRecord other) {
+        // According to RFC2782,
+        // "[a] client MUST attempt to contact the target host with the lowest-numbered priority it can reach".
+        // This means that a SRV record with a higher priority is 'less' then one with a lower.
+        int res = other.priority - this.priority;
+        if (res == 0) {
+            res = this.weight - other.weight;
+        }
+        return res;
+    }
+
+    @Override
+    public String toString() {
+        return super.toString() + " prio:" + priority + ":w:" + weight;
+    }
+}
diff --git a/src/org/jivesoftware/smack/util/package.html b/src/org/jivesoftware/smack/util/package.html
new file mode 100644
index 0000000..e34bfe3
--- /dev/null
+++ b/src/org/jivesoftware/smack/util/package.html
@@ -0,0 +1 @@
+<body>Utility classes.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/ChatState.java b/src/org/jivesoftware/smackx/ChatState.java
new file mode 100644
index 0000000..4acaa49
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ChatState.java
@@ -0,0 +1,50 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+/**
+ * Represents the current state of a users interaction with another user. Implemented according to
+ * <a href="http://www.xmpp.org/extensions/xep-0085.html">XEP-0085</a>.
+ *
+ * @author Alexander Wenckus
+ */
+public enum ChatState {
+    /**
+     * User is actively participating in the chat session.
+     */
+    active,
+    /**
+     * User is composing a message.
+     */
+    composing,
+    /**
+     * User had been composing but now has stopped.
+     */
+    paused,
+    /**
+     * User has not been actively participating in the chat session.
+     */
+    inactive,
+    /**
+     * User has effectively ended their participation in the chat session.
+     */
+    gone
+}
diff --git a/src/org/jivesoftware/smackx/ChatStateListener.java b/src/org/jivesoftware/smackx/ChatStateListener.java
new file mode 100644
index 0000000..9a1bf79
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ChatStateListener.java
@@ -0,0 +1,40 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.Chat;
+import org.jivesoftware.smack.MessageListener;
+
+/**
+ * Events for when the state of a user in a chat changes.
+ *
+ * @author Alexander Wenckus
+ */
+public interface ChatStateListener extends MessageListener {
+
+    /**
+     * Fired when the state of a chat with another user changes.
+     *
+     * @param chat the chat in which the state has changed.
+     * @param state the new state of the participant.
+     */
+    void stateChanged(Chat chat, ChatState state);
+}
diff --git a/src/org/jivesoftware/smackx/ChatStateManager.java b/src/org/jivesoftware/smackx/ChatStateManager.java
new file mode 100644
index 0000000..d452a9f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ChatStateManager.java
@@ -0,0 +1,200 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.util.collections.ReferenceMap;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.NotFilter;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.ChatStateExtension;
+
+import java.util.Map;
+import java.util.WeakHashMap;
+
+/**
+ * Handles chat state for all chats on a particular Connection. This class manages both the
+ * packet extensions and the disco response neccesary for compliance with
+ * <a href="http://www.xmpp.org/extensions/xep-0085.html">XEP-0085</a>.
+ *
+ * NOTE: {@link org.jivesoftware.smackx.ChatStateManager#getInstance(org.jivesoftware.smack.Connection)}
+ * needs to be called in order for the listeners to be registered appropriately with the connection.
+ * If this does not occur you will not receive the update notifications.
+ *
+ * @author Alexander Wenckus
+ * @see org.jivesoftware.smackx.ChatState
+ * @see org.jivesoftware.smackx.packet.ChatStateExtension
+ */
+public class ChatStateManager {
+
+    private static final Map<Connection, ChatStateManager> managers =
+            new WeakHashMap<Connection, ChatStateManager>();
+
+    private static final PacketFilter filter = new NotFilter(
+                new PacketExtensionFilter("http://jabber.org/protocol/chatstates"));
+
+    /**
+     * Returns the ChatStateManager related to the Connection and it will create one if it does
+     * not yet exist.
+     *
+     * @param connection the connection to return the ChatStateManager
+     * @return the ChatStateManager related the the connection.
+     */
+    public static ChatStateManager getInstance(final Connection connection) {
+        if(connection == null) {
+            return null;
+        }
+        synchronized (managers) {
+            ChatStateManager manager = managers.get(connection);
+            if (manager == null) {
+                manager = new ChatStateManager(connection);
+                manager.init();
+                managers.put(connection, manager);
+            }
+
+            return manager;
+        }
+    }
+
+    private final Connection connection;
+
+    private final OutgoingMessageInterceptor outgoingInterceptor = new OutgoingMessageInterceptor();
+
+    private final IncomingMessageInterceptor incomingInterceptor = new IncomingMessageInterceptor();
+
+    /**
+     * Maps chat to last chat state.
+     */
+    private final Map<Chat, ChatState> chatStates =
+            new ReferenceMap<Chat, ChatState>(ReferenceMap.WEAK, ReferenceMap.HARD);
+
+    private ChatStateManager(Connection connection) {
+        this.connection = connection;
+    }
+
+    private void init() {
+        connection.getChatManager().addOutgoingMessageInterceptor(outgoingInterceptor,
+                filter);
+        connection.getChatManager().addChatListener(incomingInterceptor);
+
+        ServiceDiscoveryManager.getInstanceFor(connection)
+                .addFeature("http://jabber.org/protocol/chatstates");
+    }
+
+    /**
+     * Sets the current state of the provided chat. This method will send an empty bodied Message
+     * packet with the state attached as a {@link org.jivesoftware.smack.packet.PacketExtension}, if
+     * and only if the new chat state is different than the last state.
+     *
+     * @param newState the new state of the chat
+     * @param chat the chat.
+     * @throws org.jivesoftware.smack.XMPPException
+     *          when there is an error sending the message
+     *          packet.
+     */
+    public void setCurrentState(ChatState newState, Chat chat) throws XMPPException {
+        if(chat == null || newState == null) {
+            throw new IllegalArgumentException("Arguments cannot be null.");
+        }
+        if(!updateChatState(chat, newState)) {
+            return;
+        }
+        Message message = new Message();
+        ChatStateExtension extension = new ChatStateExtension(newState);
+        message.addExtension(extension);
+
+        chat.sendMessage(message);
+    }
+
+
+    public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+
+        ChatStateManager that = (ChatStateManager) o;
+
+        return connection.equals(that.connection);
+
+    }
+
+    public int hashCode() {
+        return connection.hashCode();
+    }
+
+    private boolean updateChatState(Chat chat, ChatState newState) {
+        ChatState lastChatState = chatStates.get(chat);
+        if (lastChatState != newState) {
+            chatStates.put(chat, newState);
+            return true;
+        }
+        return false;
+    }
+
+    private void fireNewChatState(Chat chat, ChatState state) {
+        for (MessageListener listener : chat.getListeners()) {
+            if (listener instanceof ChatStateListener) {
+                ((ChatStateListener) listener).stateChanged(chat, state);
+            }
+        }
+    }
+
+    private class OutgoingMessageInterceptor implements PacketInterceptor {
+
+        public void interceptPacket(Packet packet) {
+            Message message = (Message) packet;
+            Chat chat = connection.getChatManager().getThreadChat(message.getThread());
+            if (chat == null) {
+                return;
+            }
+            if (updateChatState(chat, ChatState.active)) {
+                message.addExtension(new ChatStateExtension(ChatState.active));
+            }
+        }
+    }
+
+    private class IncomingMessageInterceptor implements ChatManagerListener, MessageListener {
+
+        public void chatCreated(final Chat chat, boolean createdLocally) {
+            chat.addMessageListener(this);
+        }
+
+        public void processMessage(Chat chat, Message message) {
+            PacketExtension extension
+                    = message.getExtension("http://jabber.org/protocol/chatstates");
+            if (extension == null) {
+                return;
+            }
+
+            ChatState state;
+            try {
+                state = ChatState.valueOf(extension.getElementName());
+            }
+            catch (Exception ex) {
+                return;
+            }
+
+            fireNewChatState(chat, state);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/ConfigureProviderManager.java b/src/org/jivesoftware/smackx/ConfigureProviderManager.java
new file mode 100644
index 0000000..7c0cdf2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ConfigureProviderManager.java
@@ -0,0 +1,207 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.provider.PrivacyProvider;
+import org.jivesoftware.smack.provider.ProviderManager;
+import org.jivesoftware.smackx.GroupChatInvitation;
+import org.jivesoftware.smackx.PrivateDataManager;
+import org.jivesoftware.smackx.bytestreams.ibb.provider.CloseIQProvider;
+import org.jivesoftware.smackx.bytestreams.ibb.provider.DataPacketProvider;
+import org.jivesoftware.smackx.bytestreams.ibb.provider.OpenIQProvider;
+import org.jivesoftware.smackx.bytestreams.socks5.provider.BytestreamsProvider;
+import org.jivesoftware.smackx.carbons.Carbon;
+import org.jivesoftware.smackx.entitycaps.provider.CapsExtensionProvider;
+import org.jivesoftware.smackx.forward.Forwarded;
+import org.jivesoftware.smackx.packet.AttentionExtension;
+import org.jivesoftware.smackx.packet.ChatStateExtension;
+import org.jivesoftware.smackx.packet.LastActivity;
+import org.jivesoftware.smackx.packet.Nick;
+import org.jivesoftware.smackx.packet.OfflineMessageInfo;
+import org.jivesoftware.smackx.packet.OfflineMessageRequest;
+import org.jivesoftware.smackx.packet.SharedGroupsInfo;
+import org.jivesoftware.smackx.ping.provider.PingProvider;
+import org.jivesoftware.smackx.provider.DataFormProvider;
+import org.jivesoftware.smackx.provider.DelayInformationProvider;
+import org.jivesoftware.smackx.provider.DiscoverInfoProvider;
+import org.jivesoftware.smackx.provider.DiscoverItemsProvider;
+import org.jivesoftware.smackx.provider.HeadersProvider;
+import org.jivesoftware.smackx.provider.HeaderProvider;
+import org.jivesoftware.smackx.provider.MUCAdminProvider;
+import org.jivesoftware.smackx.provider.MUCOwnerProvider;
+import org.jivesoftware.smackx.provider.MUCUserProvider;
+import org.jivesoftware.smackx.provider.MessageEventProvider;
+import org.jivesoftware.smackx.provider.MultipleAddressesProvider;
+import org.jivesoftware.smackx.provider.RosterExchangeProvider;
+import org.jivesoftware.smackx.provider.StreamInitiationProvider;
+import org.jivesoftware.smackx.provider.VCardProvider;
+import org.jivesoftware.smackx.provider.XHTMLExtensionProvider;
+import org.jivesoftware.smackx.pubsub.provider.AffiliationProvider;
+import org.jivesoftware.smackx.pubsub.provider.AffiliationsProvider;
+import org.jivesoftware.smackx.pubsub.provider.ConfigEventProvider;
+import org.jivesoftware.smackx.pubsub.provider.EventProvider;
+import org.jivesoftware.smackx.pubsub.provider.FormNodeProvider;
+import org.jivesoftware.smackx.pubsub.provider.ItemProvider;
+import org.jivesoftware.smackx.pubsub.provider.ItemsProvider;
+import org.jivesoftware.smackx.pubsub.provider.PubSubProvider;
+import org.jivesoftware.smackx.pubsub.provider.RetractEventProvider;
+import org.jivesoftware.smackx.pubsub.provider.SimpleNodeProvider;
+import org.jivesoftware.smackx.pubsub.provider.SubscriptionProvider;
+import org.jivesoftware.smackx.pubsub.provider.SubscriptionsProvider;
+import org.jivesoftware.smackx.receipts.DeliveryReceipt;
+import org.jivesoftware.smackx.search.UserSearch;
+
+/**
+ * Since dalvik on Android does not allow the loading of META-INF files from the
+ * filesystem, you have to register every provider manually.
+ *
+ * The full list of providers is at:
+ * http://fisheye.igniterealtime.org/browse/smack/trunk/build/resources/META-INF/smack.providers?hb=true
+ *
+ * @author Florian Schmaus fschmaus@gmail.com
+ *
+ */
+public class ConfigureProviderManager {
+
+    public static void configureProviderManager() {
+        ProviderManager pm = ProviderManager.getInstance();
+
+        // The order is the same as in the smack.providers file
+
+        //  Private Data Storage
+        pm.addIQProvider("query","jabber:iq:private", new PrivateDataManager.PrivateDataIQProvider());
+        //  Time
+        try {
+            pm.addIQProvider("query","jabber:iq:time", Class.forName("org.jivesoftware.smackx.packet.Time"));
+        } catch (ClassNotFoundException e) {
+            System.err.println("Can't load class for org.jivesoftware.smackx.packet.Time");
+        }
+
+        //  Roster Exchange
+        pm.addExtensionProvider("x","jabber:x:roster", new RosterExchangeProvider());
+        //  Message Events
+        pm.addExtensionProvider("x","jabber:x:event", new MessageEventProvider());
+        //  Chat State
+        pm.addExtensionProvider("active","http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider());
+        pm.addExtensionProvider("composing","http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider());
+        pm.addExtensionProvider("paused","http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider());
+        pm.addExtensionProvider("inactive","http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider());
+        pm.addExtensionProvider("gone","http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider());
+
+        //  XHTML
+        pm.addExtensionProvider("html","http://jabber.org/protocol/xhtml-im", new XHTMLExtensionProvider());
+
+        //  Group Chat Invitations
+        pm.addExtensionProvider("x","jabber:x:conference", new GroupChatInvitation.Provider());
+        //  Service Discovery # Items
+        pm.addIQProvider("query","http://jabber.org/protocol/disco#items", new DiscoverItemsProvider());
+        //  Service Discovery # Info
+        pm.addIQProvider("query","http://jabber.org/protocol/disco#info", new DiscoverInfoProvider());
+        //  Data Forms
+        pm.addExtensionProvider("x","jabber:x:data", new DataFormProvider());
+        //  MUC User
+        pm.addExtensionProvider("x","http://jabber.org/protocol/muc#user", new MUCUserProvider());
+        //  MUC Admin
+        pm.addIQProvider("query","http://jabber.org/protocol/muc#admin", new MUCAdminProvider());
+        //  MUC Owner
+        pm.addIQProvider("query","http://jabber.org/protocol/muc#owner", new MUCOwnerProvider());
+        //  Delayed Delivery
+        pm.addExtensionProvider("x","jabber:x:delay", new DelayInformationProvider());
+        pm.addExtensionProvider("delay", "urn:xmpp:delay", new DelayInformationProvider());
+        //  Version
+        try {
+            pm.addIQProvider("query","jabber:iq:version", Class.forName("org.jivesoftware.smackx.packet.Version"));
+        } catch (ClassNotFoundException e) {
+            System.err.println("Can't load class for org.jivesoftware.smackx.packet.Version");
+        }
+        //  VCard
+        pm.addIQProvider("vCard","vcard-temp", new VCardProvider());
+        //  Offline Message Requests
+        pm.addIQProvider("offline","http://jabber.org/protocol/offline", new OfflineMessageRequest.Provider());
+        //  Offline Message Indicator
+        pm.addExtensionProvider("offline","http://jabber.org/protocol/offline", new OfflineMessageInfo.Provider());
+        //  Last Activity
+        pm.addIQProvider("query","jabber:iq:last", new LastActivity.Provider());
+        //  User Search
+        pm.addIQProvider("query","jabber:iq:search", new UserSearch.Provider());
+        //  SharedGroupsInfo
+        pm.addIQProvider("sharedgroup","http://www.jivesoftware.org/protocol/sharedgroup", new SharedGroupsInfo.Provider());
+
+        //  JEP-33: Extended Stanza Addressing
+        pm.addExtensionProvider("addresses","http://jabber.org/protocol/address", new MultipleAddressesProvider());
+
+        //   FileTransfer
+        pm.addIQProvider("si","http://jabber.org/protocol/si", new StreamInitiationProvider());
+        pm.addIQProvider("query","http://jabber.org/protocol/bytestreams", new BytestreamsProvider());
+        pm.addIQProvider("open","http://jabber.org/protocol/ibb", new OpenIQProvider());
+        pm.addIQProvider("data","http://jabber.org/protocol/ibb", new DataPacketProvider());
+        pm.addIQProvider("close","http://jabber.org/protocol/ibb", new CloseIQProvider());
+        pm.addExtensionProvider("data","http://jabber.org/protocol/ibb", new DataPacketProvider());
+
+        //  Privacy
+        pm.addIQProvider("query","jabber:iq:privacy", new PrivacyProvider());
+
+        // SHIM
+        pm.addExtensionProvider("headers", "http://jabber.org/protocol/shim", new HeadersProvider());
+        pm.addExtensionProvider("header", "http://jabber.org/protocol/shim", new HeaderProvider());
+
+        // PubSub
+        pm.addIQProvider("pubsub", "http://jabber.org/protocol/pubsub", new PubSubProvider());
+        pm.addExtensionProvider("create", "http://jabber.org/protocol/pubsub", new SimpleNodeProvider());
+        pm.addExtensionProvider("items", "http://jabber.org/protocol/pubsub", new ItemsProvider());
+        pm.addExtensionProvider("item", "http://jabber.org/protocol/pubsub", new ItemProvider());
+        pm.addExtensionProvider("subscriptions", "http://jabber.org/protocol/pubsub", new SubscriptionsProvider());
+        pm.addExtensionProvider("subscription", "http://jabber.org/protocol/pubsub", new SubscriptionProvider());
+        pm.addExtensionProvider("affiliations", "http://jabber.org/protocol/pubsub", new AffiliationsProvider());
+        pm.addExtensionProvider("affiliation", "http://jabber.org/protocol/pubsub", new AffiliationProvider());
+        pm.addExtensionProvider("options", "http://jabber.org/protocol/pubsub", new FormNodeProvider());
+        // PubSub owner
+        pm.addIQProvider("pubsub", "http://jabber.org/protocol/pubsub#owner", new PubSubProvider());
+        pm.addExtensionProvider("configure", "http://jabber.org/protocol/pubsub#owner", new FormNodeProvider());
+        pm.addExtensionProvider("default", "http://jabber.org/protocol/pubsub#owner", new FormNodeProvider());
+        // PubSub event
+        pm.addExtensionProvider("event", "http://jabber.org/protocol/pubsub#event", new EventProvider());
+        pm.addExtensionProvider("configuration", "http://jabber.org/protocol/pubsub#event", new ConfigEventProvider());
+        pm.addExtensionProvider("delete", "http://jabber.org/protocol/pubsub#event", new SimpleNodeProvider());
+        pm.addExtensionProvider("options", "http://jabber.org/protocol/pubsub#event", new FormNodeProvider());
+        pm.addExtensionProvider("items", "http://jabber.org/protocol/pubsub#event", new ItemsProvider());
+        pm.addExtensionProvider("item", "http://jabber.org/protocol/pubsub#event", new ItemProvider());
+        pm.addExtensionProvider("retract", "http://jabber.org/protocol/pubsub#event", new RetractEventProvider());
+        pm.addExtensionProvider("purge", "http://jabber.org/protocol/pubsub#event", new SimpleNodeProvider());
+
+        // Nick Exchange
+        pm.addExtensionProvider("nick", "http://jabber.org/protocol/nick", new Nick.Provider());
+
+        // Attention
+        pm.addExtensionProvider("attention", "urn:xmpp:attention:0", new AttentionExtension.Provider());
+
+	// XEP-0297 Stanza Forwarding
+	pm.addExtensionProvider("forwarded", "urn:xmpp:forward:0", new Forwarded.Provider());
+
+	// XEP-0280 Message Carbons
+	pm.addExtensionProvider("sent", "urn:xmpp:carbons:2", new Carbon.Provider());
+	pm.addExtensionProvider("received", "urn:xmpp:carbons:2", new Carbon.Provider());
+
+	// XEP-0199 XMPP Ping
+	pm.addIQProvider("ping", "urn:xmpp:ping", new PingProvider());
+
+	// XEP-184 Message Delivery Receipts
+	pm.addExtensionProvider("received", "urn:xmpp:receipts", new DeliveryReceipt.Provider());
+	pm.addExtensionProvider("request", "urn:xmpp:receipts", new DeliveryReceipt.Provider());
+
+	// XEP-0115 Entity Capabilities
+	pm.addExtensionProvider("c", "http://jabber.org/protocol/caps", new CapsExtensionProvider());
+    }
+}
diff --git a/src/org/jivesoftware/smackx/DefaultMessageEventRequestListener.java b/src/org/jivesoftware/smackx/DefaultMessageEventRequestListener.java
new file mode 100644
index 0000000..7ae0c51
--- /dev/null
+++ b/src/org/jivesoftware/smackx/DefaultMessageEventRequestListener.java
@@ -0,0 +1,55 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+/**
+ *
+ * Default implementation of the MessageEventRequestListener interface.<p>
+ *
+ * This class automatically sends a delivered notification to the sender of the message 
+ * if the sender has requested to be notified when the message is delivered. 
+ *
+ * @author Gaston Dombiak
+ */
+public class DefaultMessageEventRequestListener implements MessageEventRequestListener {
+
+    public void deliveredNotificationRequested(String from, String packetID,
+                MessageEventManager messageEventManager)
+    {
+        // Send to the message's sender that the message has been delivered
+        messageEventManager.sendDeliveredNotification(from, packetID);
+    }
+
+    public void displayedNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager)
+    {
+    }
+
+    public void composingNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager)
+    {
+    }
+
+    public void offlineNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager)
+    {
+    }
+}
diff --git a/src/org/jivesoftware/smackx/Form.java b/src/org/jivesoftware/smackx/Form.java
new file mode 100644
index 0000000..992c036
--- /dev/null
+++ b/src/org/jivesoftware/smackx/Form.java
@@ -0,0 +1,551 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+import java.util.StringTokenizer;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.DataForm;
+
+/**
+ * Represents a Form for gathering data. The form could be of the following types:
+ * <ul>
+ *  <li>form -> Indicates a form to fill out.</li>
+ *  <li>submit -> The form is filled out, and this is the data that is being returned from 
+ * the form.</li>
+ *  <li>cancel -> The form was cancelled. Tell the asker that piece of information.</li>
+ *  <li>result -> Data results being returned from a search, or some other query.</li>
+ * </ul>
+ * 
+ * Depending of the form's type different operations are available. For example, it's only possible
+ * to set answers if the form is of type "submit".
+ * 
+ * @see <a href="http://xmpp.org/extensions/xep-0004.html">XEP-0004 Data Forms</a>
+ * 
+ * @author Gaston Dombiak
+ */
+public class Form {
+
+    public static final String TYPE_FORM = "form";
+    public static final String TYPE_SUBMIT = "submit";
+    public static final String TYPE_CANCEL = "cancel";
+    public static final String TYPE_RESULT = "result";
+
+    public static final String NAMESPACE = "jabber:x:data";
+    public static final String ELEMENT = "x";
+
+    private DataForm dataForm;
+
+    /**
+     * Returns a new ReportedData if the packet is used for gathering data and includes an 
+     * extension that matches the elementName and namespace "x","jabber:x:data".  
+     * 
+     * @param packet the packet used for gathering data.
+     * @return the data form parsed from the packet or <tt>null</tt> if there was not
+     *      a form in the packet.
+     */
+    public static Form getFormFrom(Packet packet) {
+        // Check if the packet includes the DataForm extension
+        PacketExtension packetExtension = packet.getExtension("x","jabber:x:data");
+        if (packetExtension != null) {
+            // Check if the existing DataForm is not a result of a search
+            DataForm dataForm = (DataForm) packetExtension;
+            if (dataForm.getReportedData() == null)
+                return new Form(dataForm);
+        }
+        // Otherwise return null
+        return null;
+    }
+
+    /**
+     * Creates a new Form that will wrap an existing DataForm. The wrapped DataForm must be
+     * used for gathering data. 
+     * 
+     * @param dataForm the data form used for gathering data. 
+     */
+    public Form(DataForm dataForm) {
+        this.dataForm = dataForm;
+    }
+    
+    /**
+     * Creates a new Form of a given type from scratch.<p>
+     *  
+     * Possible form types are:
+     * <ul>
+     *  <li>form -> Indicates a form to fill out.</li>
+     *  <li>submit -> The form is filled out, and this is the data that is being returned from 
+     * the form.</li>
+     *  <li>cancel -> The form was cancelled. Tell the asker that piece of information.</li>
+     *  <li>result -> Data results being returned from a search, or some other query.</li>
+     * </ul>
+     * 
+     * @param type the form's type (e.g. form, submit,cancel,result).
+     */
+    public Form(String type) {
+        this.dataForm = new DataForm(type);
+    }
+    
+    /**
+     * Adds a new field to complete as part of the form.
+     * 
+     * @param field the field to complete.
+     */
+    public void addField(FormField field) {
+        dataForm.addField(field);
+    }
+    
+    /**
+     * Sets a new String value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.<p>
+     * 
+     * If the value to set to the field is not a basic type (e.g. String, boolean, int, etc.) you
+     * can use this message where the String value is the String representation of the object. 
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the String value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type..
+     */
+    public void setAnswer(String variable, String value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_TEXT_MULTI.equals(field.getType())
+            && !FormField.TYPE_TEXT_PRIVATE.equals(field.getType())
+            && !FormField.TYPE_TEXT_SINGLE.equals(field.getType())
+            && !FormField.TYPE_JID_SINGLE.equals(field.getType())
+            && !FormField.TYPE_HIDDEN.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type String.");
+        }
+        setAnswer(field, value);
+    }
+
+    /**
+     * Sets a new int value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the int value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type.
+     */
+    public void setAnswer(String variable, int value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_TEXT_MULTI.equals(field.getType())
+            && !FormField.TYPE_TEXT_PRIVATE.equals(field.getType())
+            && !FormField.TYPE_TEXT_SINGLE.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type int.");
+        }
+        setAnswer(field, value);
+    }
+
+    /**
+     * Sets a new long value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the long value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type.
+     */
+    public void setAnswer(String variable, long value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_TEXT_MULTI.equals(field.getType())
+            && !FormField.TYPE_TEXT_PRIVATE.equals(field.getType())
+            && !FormField.TYPE_TEXT_SINGLE.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type long.");
+        }
+        setAnswer(field, value);
+    }
+
+    /**
+     * Sets a new float value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the float value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type.
+     */
+    public void setAnswer(String variable, float value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_TEXT_MULTI.equals(field.getType())
+            && !FormField.TYPE_TEXT_PRIVATE.equals(field.getType())
+            && !FormField.TYPE_TEXT_SINGLE.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type float.");
+        }
+        setAnswer(field, value);
+    }
+
+    /**
+     * Sets a new double value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the double value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type.
+     */
+    public void setAnswer(String variable, double value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_TEXT_MULTI.equals(field.getType())
+            && !FormField.TYPE_TEXT_PRIVATE.equals(field.getType())
+            && !FormField.TYPE_TEXT_SINGLE.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type double.");
+        }
+        setAnswer(field, value);
+    }
+
+    /**
+     * Sets a new boolean value to a given form's field. The field whose variable matches the 
+     * requested variable will be completed with the specified value. If no field could be found 
+     * for the specified variable then an exception will be raised.
+     * 
+     * @param variable the variable name that was completed.
+     * @param value the boolean value that was answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable or
+     *      if the answer type does not correspond with the field type.
+     */
+    public void setAnswer(String variable, boolean value) {
+        FormField field = getField(variable);
+        if (field == null) {
+            throw new IllegalArgumentException("Field not found for the specified variable name.");
+        }
+        if (!FormField.TYPE_BOOLEAN.equals(field.getType())) {
+            throw new IllegalArgumentException("This field is not of type boolean.");
+        }
+        setAnswer(field, (value ? "1" : "0"));
+    }
+
+    /**
+     * Sets a new Object value to a given form's field. In fact, the object representation 
+     * (i.e. #toString) will be the actual value of the field.<p>
+     * 
+     * If the value to set to the field is not a basic type (e.g. String, boolean, int, etc.) you
+     * will need to use {@link #setAnswer(String, String))} where the String value is the 
+     * String representation of the object.<p> 
+     * 
+     * Before setting the new value to the field we will check if the form is of type submit. If 
+     * the form isn't of type submit means that it's not possible to complete the form and an   
+     * exception will be thrown.
+     * 
+     * @param field the form field that was completed.
+     * @param value the Object value that was answered. The object representation will be the 
+     * actual value.
+     * @throws IllegalStateException if the form is not of type "submit".
+     */
+    private void setAnswer(FormField field, Object value) {
+        if (!isSubmitType()) {
+            throw new IllegalStateException("Cannot set an answer if the form is not of type " +
+            "\"submit\"");
+        }
+        field.resetValues();
+        field.addValue(value.toString());
+    }
+
+    /**
+     * Sets a new values to a given form's field. The field whose variable matches the requested 
+     * variable will be completed with the specified values. If no field could be found for 
+     * the specified variable then an exception will be raised.<p>
+     * 
+     * The Objects contained in the List could be of any type. The String representation of them
+     * (i.e. #toString) will be actually used when sending the answer to the server.
+     * 
+     * @param variable the variable that was completed.
+     * @param values the values that were answered.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable.
+     */
+    public void setAnswer(String variable, List<String> values) {
+        if (!isSubmitType()) {
+            throw new IllegalStateException("Cannot set an answer if the form is not of type " +
+            "\"submit\"");
+        }
+        FormField field = getField(variable);
+        if (field != null) {
+            // Check that the field can accept a collection of values
+            if (!FormField.TYPE_JID_MULTI.equals(field.getType())
+                && !FormField.TYPE_LIST_MULTI.equals(field.getType())
+                && !FormField.TYPE_LIST_SINGLE.equals(field.getType())
+                && !FormField.TYPE_TEXT_MULTI.equals(field.getType())
+                && !FormField.TYPE_HIDDEN.equals(field.getType())) {
+                throw new IllegalArgumentException("This field only accept list of values.");
+            }
+            // Clear the old values 
+            field.resetValues();
+            // Set the new values. The string representation of each value will be actually used.
+            field.addValues(values);
+        }
+        else {
+            throw new IllegalArgumentException("Couldn't find a field for the specified variable.");
+        }
+    }
+
+    /**
+     * Sets the default value as the value of a given form's field. The field whose variable matches
+     * the requested variable will be completed with its default value. If no field could be found
+     * for the specified variable then an exception will be raised.
+     *
+     * @param variable the variable to complete with its default value.
+     * @throws IllegalStateException if the form is not of type "submit".
+     * @throws IllegalArgumentException if the form does not include the specified variable.
+     */
+    public void setDefaultAnswer(String variable) {
+        if (!isSubmitType()) {
+            throw new IllegalStateException("Cannot set an answer if the form is not of type " +
+            "\"submit\"");
+        }
+        FormField field = getField(variable);
+        if (field != null) {
+            // Clear the old values
+            field.resetValues();
+            // Set the default value
+            for (Iterator<String> it = field.getValues(); it.hasNext();) {
+                field.addValue(it.next());
+            }
+        }
+        else {
+            throw new IllegalArgumentException("Couldn't find a field for the specified variable.");
+        }
+    }
+
+    /**
+     * Returns an Iterator for the fields that are part of the form.
+     *
+     * @return an Iterator for the fields that are part of the form.
+     */
+    public Iterator<FormField> getFields() {
+        return dataForm.getFields();
+    }
+
+    /**
+     * Returns the field of the form whose variable matches the specified variable.
+     * The fields of type FIXED will never be returned since they do not specify a 
+     * variable. 
+     * 
+     * @param variable the variable to look for in the form fields. 
+     * @return the field of the form whose variable matches the specified variable.
+     */
+    public FormField getField(String variable) {
+        if (variable == null || variable.equals("")) {
+            throw new IllegalArgumentException("Variable must not be null or blank.");
+        }
+        // Look for the field whose variable matches the requested variable
+        FormField field;
+        for (Iterator<FormField> it=getFields();it.hasNext();) {
+            field = it.next();
+            if (variable.equals(field.getVariable())) {
+                return field;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Returns the instructions that explain how to fill out the form and what the form is about.
+     * 
+     * @return instructions that explain how to fill out the form.
+     */
+    public String getInstructions() {
+        StringBuilder sb = new StringBuilder();
+        // Join the list of instructions together separated by newlines
+        for (Iterator<String> it = dataForm.getInstructions(); it.hasNext();) {
+            sb.append(it.next());
+            // If this is not the last instruction then append a newline
+            if (it.hasNext()) {
+                sb.append("\n");
+            }
+        }
+        return sb.toString();
+    }
+
+
+    /**
+     * Returns the description of the data. It is similar to the title on a web page or an X 
+     * window.  You can put a <title/> on either a form to fill out, or a set of data results.
+     * 
+     * @return description of the data.
+     */
+    public String getTitle() {
+        return dataForm.getTitle();
+    }
+
+
+    /**
+     * Returns the meaning of the data within the context. The data could be part of a form
+     * to fill out, a form submission or data results.<p>
+     * 
+     * Possible form types are:
+     * <ul>
+     *  <li>form -> Indicates a form to fill out.</li>
+     *  <li>submit -> The form is filled out, and this is the data that is being returned from 
+     * the form.</li>
+     *  <li>cancel -> The form was cancelled. Tell the asker that piece of information.</li>
+     *  <li>result -> Data results being returned from a search, or some other query.</li>
+     * </ul>
+     * 
+     * @return the form's type.
+     */
+    public String getType() {
+        return dataForm.getType(); 
+    }
+    
+
+    /**
+     * Sets instructions that explain how to fill out the form and what the form is about.
+     * 
+     * @param instructions instructions that explain how to fill out the form.
+     */
+    public void setInstructions(String instructions) {
+        // Split the instructions into multiple instructions for each existent newline
+        ArrayList<String> instructionsList = new ArrayList<String>();
+        StringTokenizer st = new StringTokenizer(instructions, "\n");
+        while (st.hasMoreTokens()) {
+            instructionsList.add(st.nextToken());
+        }
+        // Set the new list of instructions
+        dataForm.setInstructions(instructionsList);
+        
+    }
+
+
+    /**
+     * Sets the description of the data. It is similar to the title on a web page or an X window.
+     * You can put a <title/> on either a form to fill out, or a set of data results.
+     * 
+     * @param title description of the data.
+     */
+    public void setTitle(String title) {
+        dataForm.setTitle(title);
+    }
+    
+    /**
+     * Returns a DataForm that serves to send this Form to the server. If the form is of type 
+     * submit, it may contain fields with no value. These fields will be removed since they only 
+     * exist to assist the user while editing/completing the form in a UI. 
+     * 
+     * @return the wrapped DataForm.
+     */
+    public DataForm getDataFormToSend() {
+        if (isSubmitType()) {
+            // Create a new DataForm that contains only the answered fields 
+            DataForm dataFormToSend = new DataForm(getType());
+            for(Iterator<FormField> it=getFields();it.hasNext();) {
+                FormField field = it.next();
+                if (field.getValues().hasNext()) {
+                    dataFormToSend.addField(field);
+                }
+            }
+            return dataFormToSend;
+        }
+        return dataForm;
+    }
+    
+    /**
+     * Returns true if the form is a form to fill out.
+     * 
+     * @return if the form is a form to fill out.
+     */
+    private boolean isFormType() {
+        return TYPE_FORM.equals(dataForm.getType());
+    }
+    
+    /**
+     * Returns true if the form is a form to submit.
+     * 
+     * @return if the form is a form to submit.
+     */
+    private boolean isSubmitType() {
+        return TYPE_SUBMIT.equals(dataForm.getType());
+    }
+
+    /**
+     * Returns a new Form to submit the completed values. The new Form will include all the fields
+     * of the original form except for the fields of type FIXED. Only the HIDDEN fields will 
+     * include the same value of the original form. The other fields of the new form MUST be 
+     * completed. If a field remains with no answer when sending the completed form, then it won't 
+     * be included as part of the completed form.<p>
+     * 
+     * The reason why the fields with variables are included in the new form is to provide a model 
+     * for binding with any UI. This means that the UIs will use the original form (of type 
+     * "form") to learn how to render the form, but the UIs will bind the fields to the form of
+     * type submit.
+     * 
+     * @return a Form to submit the completed values.
+     */
+    public Form createAnswerForm() {
+        if (!isFormType()) {
+            throw new IllegalStateException("Only forms of type \"form\" could be answered");
+        }
+        // Create a new Form
+        Form form = new Form(TYPE_SUBMIT);
+        for (Iterator<FormField> fields=getFields(); fields.hasNext();) {
+            FormField field = fields.next();
+            // Add to the new form any type of field that includes a variable.
+            // Note: The fields of type FIXED are the only ones that don't specify a variable
+            if (field.getVariable() != null) {
+                FormField newField = new FormField(field.getVariable());
+                newField.setType(field.getType());
+                form.addField(newField);
+                // Set the answer ONLY to the hidden fields 
+                if (FormField.TYPE_HIDDEN.equals(field.getType())) {
+                    // Since a hidden field could have many values we need to collect them 
+                    // in a list
+                    List<String> values = new ArrayList<String>();
+                    for (Iterator<String> it=field.getValues();it.hasNext();) {
+                        values.add(it.next());
+                    }
+                    form.setAnswer(field.getVariable(), values);
+                }                
+            }
+        }
+        return form;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/FormField.java b/src/org/jivesoftware/smackx/FormField.java
new file mode 100644
index 0000000..3d15e92
--- /dev/null
+++ b/src/org/jivesoftware/smackx/FormField.java
@@ -0,0 +1,409 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents a field of a form. The field could be used to represent a question to complete,
+ * a completed question or a data returned from a search. The exact interpretation of the field
+ * depends on the context where the field is used.
+ *
+ * @author Gaston Dombiak
+ */
+public class FormField {
+
+    public static final String TYPE_BOOLEAN = "boolean";
+    public static final String TYPE_FIXED = "fixed";
+    public static final String TYPE_HIDDEN = "hidden";
+    public static final String TYPE_JID_MULTI = "jid-multi";
+    public static final String TYPE_JID_SINGLE = "jid-single";
+    public static final String TYPE_LIST_MULTI = "list-multi";
+    public static final String TYPE_LIST_SINGLE = "list-single";
+    public static final String TYPE_TEXT_MULTI = "text-multi";
+    public static final String TYPE_TEXT_PRIVATE = "text-private";
+    public static final String TYPE_TEXT_SINGLE = "text-single";
+
+    private String description;
+    private boolean required = false;
+    private String label;
+    private String variable;
+    private String type;
+    private final List<Option> options = new ArrayList<Option>();
+    private final List<String> values = new ArrayList<String>();
+
+    /**
+     * Creates a new FormField with the variable name that uniquely identifies the field
+     * in the context of the form.
+     *
+     * @param variable the variable name of the question.
+     */
+    public FormField(String variable) {
+        this.variable = variable;
+    }
+
+    /**
+     * Creates a new FormField of type FIXED. The fields of type FIXED do not define a variable
+     * name.
+     */
+    public FormField() {
+        this.type = FormField.TYPE_FIXED;
+    }
+
+    /**
+     * Returns a description that provides extra clarification about the question. This information
+     * could be presented to the user either in tool-tip, help button, or as a section of text
+     * before the question.<p>
+     * <p/>
+     * If the question is of type FIXED then the description should remain empty.
+     *
+     * @return description that provides extra clarification about the question.
+     */
+    public String getDescription() {
+        return description;
+    }
+
+    /**
+     * Returns the label of the question which should give enough information to the user to
+     * fill out the form.
+     *
+     * @return label of the question.
+     */
+    public String getLabel() {
+        return label;
+    }
+
+    /**
+     * Returns an Iterator for the available options that the user has in order to answer
+     * the question.
+     *
+     * @return Iterator for the available options.
+     */
+    public Iterator<Option> getOptions() {
+        synchronized (options) {
+            return Collections.unmodifiableList(new ArrayList<Option>(options)).iterator();
+        }
+    }
+
+    /**
+     * Returns true if the question must be answered in order to complete the questionnaire.
+     *
+     * @return true if the question must be answered in order to complete the questionnaire.
+     */
+    public boolean isRequired() {
+        return required;
+    }
+
+    /**
+     * Returns an indicative of the format for the data to answer. Valid formats are:
+     * <p/>
+     * <ul>
+     * <li>text-single -> single line or word of text
+     * <li>text-private -> instead of showing the user what they typed, you show ***** to
+     * protect it
+     * <li>text-multi -> multiple lines of text entry
+     * <li>list-single -> given a list of choices, pick one
+     * <li>list-multi -> given a list of choices, pick one or more
+     * <li>boolean -> 0 or 1, true or false, yes or no. Default value is 0
+     * <li>fixed -> fixed for putting in text to show sections, or just advertise your web
+     * site in the middle of the form
+     * <li>hidden -> is not given to the user at all, but returned with the questionnaire
+     * <li>jid-single -> Jabber ID - choosing a JID from your roster, and entering one based
+     * on the rules for a JID.
+     * <li>jid-multi -> multiple entries for JIDs
+     * </ul>
+     *
+     * @return format for the data to answer.
+     */
+    public String getType() {
+        return type;
+    }
+
+    /**
+     * Returns an Iterator for the default values of the question if the question is part
+     * of a form to fill out. Otherwise, returns an Iterator for the answered values of
+     * the question.
+     *
+     * @return an Iterator for the default values or answered values of the question.
+     */
+    public Iterator<String> getValues() {
+        synchronized (values) {
+            return Collections.unmodifiableList(new ArrayList<String>(values)).iterator();
+        }
+    }
+
+    /**
+     * Returns the variable name that the question is filling out.
+     *
+     * @return the variable name of the question.
+     */
+    public String getVariable() {
+        return variable;
+    }
+
+    /**
+     * Sets a description that provides extra clarification about the question. This information
+     * could be presented to the user either in tool-tip, help button, or as a section of text
+     * before the question.<p>
+     * <p/>
+     * If the question is of type FIXED then the description should remain empty.
+     *
+     * @param description provides extra clarification about the question.
+     */
+    public void setDescription(String description) {
+        this.description = description;
+    }
+
+    /**
+     * Sets the label of the question which should give enough information to the user to
+     * fill out the form.
+     *
+     * @param label the label of the question.
+     */
+    public void setLabel(String label) {
+        this.label = label;
+    }
+
+    /**
+     * Sets if the question must be answered in order to complete the questionnaire.
+     *
+     * @param required if the question must be answered in order to complete the questionnaire.
+     */
+    public void setRequired(boolean required) {
+        this.required = required;
+    }
+
+    /**
+     * Sets an indicative of the format for the data to answer. Valid formats are:
+     * <p/>
+     * <ul>
+     * <li>text-single -> single line or word of text
+     * <li>text-private -> instead of showing the user what they typed, you show ***** to
+     * protect it
+     * <li>text-multi -> multiple lines of text entry
+     * <li>list-single -> given a list of choices, pick one
+     * <li>list-multi -> given a list of choices, pick one or more
+     * <li>boolean -> 0 or 1, true or false, yes or no. Default value is 0
+     * <li>fixed -> fixed for putting in text to show sections, or just advertise your web
+     * site in the middle of the form
+     * <li>hidden -> is not given to the user at all, but returned with the questionnaire
+     * <li>jid-single -> Jabber ID - choosing a JID from your roster, and entering one based
+     * on the rules for a JID.
+     * <li>jid-multi -> multiple entries for JIDs
+     * </ul>
+     *
+     * @param type an indicative of the format for the data to answer.
+     */
+    public void setType(String type) {
+        this.type = type;
+    }
+
+    /**
+     * Adds a default value to the question if the question is part of a form to fill out.
+     * Otherwise, adds an answered value to the question.
+     *
+     * @param value a default value or an answered value of the question.
+     */
+    public void addValue(String value) {
+        synchronized (values) {
+            values.add(value);
+        }
+    }
+
+    /**
+     * Adds a default values to the question if the question is part of a form to fill out.
+     * Otherwise, adds an answered values to the question.
+     *
+     * @param newValues default values or an answered values of the question.
+     */
+    public void addValues(List<String> newValues) {
+        synchronized (values) {
+            values.addAll(newValues);
+        }
+    }
+
+    /**
+     * Removes all the values of the field.
+     */
+    protected void resetValues() {
+        synchronized (values) {
+            values.removeAll(new ArrayList<String>(values));
+        }
+    }
+
+    /**
+     * Adss an available options to the question that the user has in order to answer
+     * the question.
+     *
+     * @param option a new available option for the question.
+     */
+    public void addOption(Option option) {
+        synchronized (options) {
+            options.add(option);
+        }
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<field");
+        // Add attributes
+        if (getLabel() != null) {
+            buf.append(" label=\"").append(getLabel()).append("\"");
+        }
+        if (getVariable() != null) {
+            buf.append(" var=\"").append(getVariable()).append("\"");
+        }
+        if (getType() != null) {
+            buf.append(" type=\"").append(getType()).append("\"");
+        }
+        buf.append(">");
+        // Add elements
+        if (getDescription() != null) {
+            buf.append("<desc>").append(getDescription()).append("</desc>");
+        }
+        if (isRequired()) {
+            buf.append("<required/>");
+        }
+        // Loop through all the values and append them to the string buffer
+        for (Iterator<String> i = getValues(); i.hasNext();) {
+            buf.append("<value>").append(i.next()).append("</value>");
+        }
+        // Loop through all the values and append them to the string buffer
+        for (Iterator<Option> i = getOptions(); i.hasNext();) {
+            buf.append((i.next()).toXML());
+        }
+        buf.append("</field>");
+        return buf.toString();
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (obj == null)
+            return false;
+        if (obj == this)
+            return true;
+        if (!(obj instanceof FormField))
+            return false;
+
+        FormField other = (FormField) obj;
+
+        return toXML().equals(other.toXML());
+    }
+
+    @Override
+    public int hashCode() {
+        return toXML().hashCode();
+    }
+
+    /**
+     * Represents the available option of a given FormField.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Option {
+
+        private String label;
+        private String value;
+
+        public Option(String value) {
+            this.value = value;
+        }
+
+        public Option(String label, String value) {
+            this.label = label;
+            this.value = value;
+        }
+
+        /**
+         * Returns the label that represents the option.
+         *
+         * @return the label that represents the option.
+         */
+        public String getLabel() {
+            return label;
+        }
+
+        /**
+         * Returns the value of the option.
+         *
+         * @return the value of the option.
+         */
+        public String getValue() {
+            return value;
+        }
+
+        @Override
+        public String toString() {
+            return getLabel();
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<option");
+            // Add attribute
+            if (getLabel() != null) {
+                buf.append(" label=\"").append(getLabel()).append("\"");
+            }
+            buf.append(">");
+            // Add element
+            buf.append("<value>").append(StringUtils.escapeForXML(getValue())).append("</value>");
+
+            buf.append("</option>");
+            return buf.toString();
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (obj == null)
+                return false;
+            if (obj == this)
+                return true;
+            if (obj.getClass() != getClass())
+                return false;
+
+            Option other = (Option) obj;
+
+            if (!value.equals(other.value))
+                return false;
+
+            String thisLabel = label == null ? "" : label;
+            String otherLabel = other.label == null ? "" : other.label;
+
+            if (!thisLabel.equals(otherLabel))
+                return false;
+
+            return true;
+        }
+
+        @Override
+        public int hashCode() {
+            int result = 1;
+            result = 37 * result + value.hashCode();
+            result = 37 * result + (label == null ? 0 : label.hashCode());
+            return result;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/Gateway.java b/src/org/jivesoftware/smackx/Gateway.java
new file mode 100644
index 0000000..5b5836f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/Gateway.java
@@ -0,0 +1,333 @@
+package org.jivesoftware.smackx;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Roster;
+import org.jivesoftware.smack.RosterEntry;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.Registration;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+
+/**
+ * This class provides an abstract view to gateways/transports. This class handles all
+ * actions regarding gateways and transports.
+ * @author Till Klocke
+ *
+ */
+public class Gateway {
+	
+	private Connection connection;
+	private ServiceDiscoveryManager sdManager;
+	private Roster roster;
+	private String entityJID;
+	private Registration registerInfo;
+	private Identity identity;
+	private DiscoverInfo info;
+	
+	Gateway(Connection connection, String entityJID){
+		this.connection = connection;
+		this.roster = connection.getRoster();
+		this.sdManager = ServiceDiscoveryManager.getInstanceFor(connection);
+		this.entityJID = entityJID;
+	}
+	
+	Gateway(Connection connection, String entityJID, DiscoverInfo info, Identity identity){
+		this(connection, entityJID);
+		this.info = info;
+		this.identity = identity;
+	}
+	
+	private void discoverInfo() throws XMPPException{
+		info = sdManager.discoverInfo(entityJID);
+		Iterator<Identity> iterator = info.getIdentities();
+		while(iterator.hasNext()){
+			Identity temp = iterator.next();
+			if(temp.getCategory().equalsIgnoreCase("gateway")){
+				this.identity = temp;
+				break;
+			}
+		}
+	}
+	
+	private Identity getIdentity() throws XMPPException{
+		if(identity==null){
+			discoverInfo();
+		}
+		return identity;
+	}
+	
+	private Registration getRegisterInfo(){
+		if(registerInfo==null){
+			refreshRegisterInfo();
+		}
+		return registerInfo;
+	}
+	
+	private void refreshRegisterInfo(){
+		Registration packet = new Registration();
+		packet.setFrom(connection.getUser());
+		packet.setType(IQ.Type.GET);
+		packet.setTo(entityJID);
+		PacketCollector collector = 
+			connection.createPacketCollector(new PacketIDFilter(packet.getPacketID()));
+		connection.sendPacket(packet);
+		Packet result = collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+		collector.cancel();
+		if(result instanceof Registration && result.getError()==null){ 
+			Registration register = (Registration)result;
+			this.registerInfo = register;
+		}
+	}
+	
+	/**
+	 * Checks if this gateway supports In-Band registration
+	 * @return true if In-Band registration is supported
+	 * @throws XMPPException
+	 */
+	public boolean canRegister() throws XMPPException{
+		if(info==null){
+			discoverInfo();
+		}
+		return info.containsFeature("jabber:iq:register");
+	}
+	
+	/**
+	 * Returns all fields that are required to register to this gateway
+	 * @return a list of required fields
+	 */
+	public List<String> getRequiredFields(){
+		return getRegisterInfo().getRequiredFields();
+	}
+	
+	/**
+	 * Returns the name as proposed in this gateways identity discovered via service
+	 * discovery
+	 * @return a String of its name
+	 * @throws XMPPException
+	 */
+	public String getName() throws XMPPException{
+		if(identity==null){
+			discoverInfo();
+		}
+		return identity.getName();
+	}
+	
+	/**
+	 * Returns the type as proposed in this gateways identity discovered via service
+	 * discovery. See {@link http://xmpp.org/registrar/disco-categories.html} for 
+	 * possible types
+	 * @return a String describing the type
+	 * @throws XMPPException
+	 */
+	public String getType() throws XMPPException{
+		if(identity==null){
+			discoverInfo();
+		}
+		return identity.getType();
+	}
+	
+	/**
+	 * Returns true if the registration informations indicates that you are already 
+	 * registered with this gateway
+	 * @return true if already registered
+	 * @throws XMPPException
+	 */
+	public boolean isRegistered() throws XMPPException{
+		return getRegisterInfo().isRegistered();
+	}
+	
+	/**
+	 * Returns the value of specific field of the registration information. Can be used
+	 * to retrieve for example to retrieve username/password used on an already registered
+	 * gateway.
+	 * @param fieldName name of the field
+	 * @return a String containing the value of the field or null
+	 */
+	public String getField(String fieldName){
+		return getRegisterInfo().getField(fieldName);
+	}
+	
+	/**
+	 * Returns a List of Strings of all field names which contain values.
+	 * @return a List of field names
+	 */
+	public List<String> getFieldNames(){
+		return getRegisterInfo().getFieldNames();
+	}
+	
+	/**
+	 * A convenience method for retrieving the username of an existing account 
+	 * @return String describing the username
+	 */
+	public String getUsername(){
+		return getField("username");
+	}
+	
+	/**
+	 * A convenience method for retrieving the password of an existing accoung
+	 * @return String describing the password
+	 */
+	public String getPassword(){
+		return getField("password");
+	}
+	
+	/**
+	 * Returns instructions for registering with this gateway
+	 * @return String containing instructions
+	 */
+	public String getInstructions(){
+		return getRegisterInfo().getInstructions();	
+	}
+	
+	/**
+	 * With this method you can register with this gateway or modify an existing registration
+	 * @param username String describing the username
+	 * @param password String describing the password
+	 * @param fields additional fields like email.
+	 * @throws XMPPException 
+	 */
+	public void register(String username, String password, Map<String,String> fields)throws XMPPException{
+		if(getRegisterInfo().isRegistered()) {
+			throw new IllegalStateException("You are already registered with this gateway");
+		}
+		Registration register = new Registration();
+		register.setFrom(connection.getUser());
+		register.setTo(entityJID);
+		register.setType(IQ.Type.SET);
+		register.setUsername(username);
+		register.setPassword(password);
+		for(String s : fields.keySet()){
+			register.addAttribute(s, fields.get(s));
+		}
+		PacketCollector resultCollector = 
+			connection.createPacketCollector(new PacketIDFilter(register.getPacketID())); 
+		connection.sendPacket(register);
+		Packet result = 
+			resultCollector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+		resultCollector.cancel();
+		if(result!=null && result instanceof IQ){
+			IQ resultIQ = (IQ)result;
+			if(resultIQ.getError()!=null){
+				throw new XMPPException(resultIQ.getError());
+			}
+			if(resultIQ.getType()==IQ.Type.ERROR){
+				throw new XMPPException(resultIQ.getError());
+			}
+			connection.addPacketListener(new GatewayPresenceListener(), 
+					new PacketTypeFilter(Presence.class));
+			roster.createEntry(entityJID, getIdentity().getName(), new String[]{});
+		}
+		else{
+			throw new XMPPException("Packet reply timeout");
+		}
+	}
+	
+	/**
+	 * A convenience method for registering or modifying an account on this gateway without
+	 * additional fields
+	 * @param username String describing the username
+	 * @param password String describing the password
+	 * @throws XMPPException
+	 */
+	public void register(String username, String password) throws XMPPException{
+		register(username, password,new HashMap<String,String>());
+	}
+	
+	/**
+	 * This method removes an existing registration from this gateway
+	 * @throws XMPPException
+	 */
+	public void unregister() throws XMPPException{
+		Registration register = new Registration();
+		register.setFrom(connection.getUser());
+		register.setTo(entityJID);
+		register.setType(IQ.Type.SET);
+		register.setRemove(true);
+		PacketCollector resultCollector = 
+			connection.createPacketCollector(new PacketIDFilter(register.getPacketID()));
+		connection.sendPacket(register);
+		Packet result = resultCollector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+		resultCollector.cancel();
+		if(result!=null && result instanceof IQ){
+			IQ resultIQ = (IQ)result;
+			if(resultIQ.getError()!=null){
+				throw new XMPPException(resultIQ.getError());
+			}
+			if(resultIQ.getType()==IQ.Type.ERROR){
+				throw new XMPPException(resultIQ.getError());
+			}
+			RosterEntry gatewayEntry = roster.getEntry(entityJID);
+			roster.removeEntry(gatewayEntry);
+		}
+		else{
+			throw new XMPPException("Packet reply timeout");
+		}
+	}
+	
+	/**
+	 * Lets you login manually in this gateway. Normally a gateway logins you when it
+	 * receives the first presence broadcasted by your server. But it is possible to
+	 * manually login and logout by sending a directed presence. This method sends an
+	 * empty available presence direct to the gateway.
+	 */
+	public void login(){
+		Presence presence = new Presence(Presence.Type.available);
+		login(presence);
+	}
+	
+	/**
+	 * This method lets you send the presence direct to the gateway. Type, To and From
+	 * are modified.
+	 * @param presence the presence used to login to gateway
+	 */
+	public void login(Presence presence){
+		presence.setType(Presence.Type.available);
+		presence.setTo(entityJID);
+		presence.setFrom(connection.getUser());
+		connection.sendPacket(presence);
+	}
+	
+	/**
+	 * This method logs you out from this gateway by sending an unavailable presence
+	 * to directly to this gateway.
+	 */
+	public void logout(){
+		Presence presence = new Presence(Presence.Type.unavailable);
+		presence.setTo(entityJID);
+		presence.setFrom(connection.getUser());
+		connection.sendPacket(presence);
+	}
+	
+	private class GatewayPresenceListener implements PacketListener{
+
+		public void processPacket(Packet packet) {
+			if(packet instanceof Presence){
+				Presence presence = (Presence)packet;
+				if(entityJID.equals(presence.getFrom()) && 
+						roster.contains(presence.getFrom()) &&
+						presence.getType().equals(Presence.Type.subscribe)){
+					Presence response = new Presence(Presence.Type.subscribed);
+					response.setTo(presence.getFrom());
+					response.setFrom(StringUtils.parseBareAddress(connection.getUser()));
+					connection.sendPacket(response);
+				}
+			}
+			
+		}
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/GatewayManager.java b/src/org/jivesoftware/smackx/GatewayManager.java
new file mode 100644
index 0000000..eee9cfc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/GatewayManager.java
@@ -0,0 +1,199 @@
+package org.jivesoftware.smackx;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.Roster;
+import org.jivesoftware.smack.RosterEntry;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+import org.jivesoftware.smackx.packet.DiscoverItems.Item;
+
+/**
+ * This class is the general entry point to gateway interaction (XEP-0100). 
+ * This class discovers available gateways on the users servers, and
+ * can give you also a list of gateways the you user is registered with which
+ * are not on his server. All actual interaction with a gateway is handled in the
+ * class {@see Gateway}.
+ * @author Till Klocke
+ *
+ */
+public class GatewayManager {
+	
+	private static Map<Connection,GatewayManager> instances = 
+		new HashMap<Connection,GatewayManager>();
+	
+	private ServiceDiscoveryManager sdManager;
+	
+	private Map<String,Gateway> localGateways = new HashMap<String,Gateway>();
+	
+	private Map<String,Gateway> nonLocalGateways = new HashMap<String,Gateway>();
+	
+	private Map<String,Gateway> gateways = new HashMap<String,Gateway>();
+	
+	private Connection connection;
+	
+	private Roster roster;
+	
+	private GatewayManager(){
+		
+	}
+	
+	/**
+	 * Creates a new instance of GatewayManager
+	 * @param connection
+	 * @throws XMPPException
+	 */
+	private GatewayManager(Connection connection) throws XMPPException{
+		this.connection = connection;
+		this.roster = connection.getRoster();
+		sdManager = ServiceDiscoveryManager.getInstanceFor(connection);
+	}
+	
+	/**
+	 * Loads all gateways the users server offers
+	 * @throws XMPPException
+	 */
+	private void loadLocalGateways() throws XMPPException{
+		DiscoverItems items = sdManager.discoverItems(connection.getHost());
+		Iterator<Item> iter = items.getItems();
+		while(iter.hasNext()){
+			String itemJID = iter.next().getEntityID();
+			discoverGateway(itemJID);
+		}
+	}
+	
+	/**
+	 * Discovers {@link DiscoveryInfo} and {@link DiscoveryInfo.Identity} of a gateway
+	 * and creates a {@link Gateway} object representing this gateway.
+	 * @param itemJID
+	 * @throws XMPPException
+	 */
+	private void discoverGateway(String itemJID) throws XMPPException{
+		DiscoverInfo info = sdManager.discoverInfo(itemJID);
+		Iterator<Identity> i = info.getIdentities();
+		
+		while(i.hasNext()){
+			Identity identity = i.next();
+			String category = identity.getCategory();
+			if(category.toLowerCase().equals("gateway")){
+				gateways.put(itemJID, new Gateway(connection,itemJID));
+				if(itemJID.contains(connection.getHost())){
+					localGateways.put(itemJID, 
+							new Gateway(connection,itemJID,info,identity));
+				}
+				else{
+					nonLocalGateways.put(itemJID, 
+							new Gateway(connection,itemJID,info,identity));
+				}
+				break;
+			}
+		}
+	}
+	
+	/**
+	 * Loads all getways which are in the users roster, but are not supplied by the
+	 * users server
+	 * @throws XMPPException
+	 */
+	private void loadNonLocalGateways() throws XMPPException{
+		if(roster!=null){
+			for(RosterEntry entry : roster.getEntries()){
+				if(entry.getUser().equalsIgnoreCase(StringUtils.parseServer(entry.getUser())) &&
+						!entry.getUser().contains(connection.getHost())){
+					discoverGateway(entry.getUser());
+				}
+			}
+		}
+	}
+	
+	/**
+	 * Returns an instance of GatewayManager for the given connection. If no instance for
+	 * this connection exists a new one is created and stored in a Map.
+	 * @param connection
+	 * @return an instance of GatewayManager
+	 * @throws XMPPException
+	 */
+	public GatewayManager getInstanceFor(Connection connection) throws XMPPException{
+		synchronized(instances){
+			if(instances.containsKey(connection)){
+				return instances.get(connection);
+			}
+			GatewayManager instance = new GatewayManager(connection);
+			instances.put(connection, instance);
+			return instance;
+		}
+	}
+	
+	/**
+	 * Returns a list of gateways which are offered by the users server, wether the
+	 * user is registered to them or not.
+	 * @return a List of Gateways
+	 * @throws XMPPException
+	 */
+	public List<Gateway> getLocalGateways() throws XMPPException{
+		if(localGateways.size()==0){
+			loadLocalGateways();
+		}
+		return new ArrayList<Gateway>(localGateways.values());
+	}
+	
+	/**
+	 * Returns a list of gateways the user has in his roster, but which are offered by
+	 * remote servers. But note that this list isn't automatically refreshed. You have to
+	 * refresh is manually if needed.
+	 * @return a list of gateways
+	 * @throws XMPPException
+	 */
+	public List<Gateway> getNonLocalGateways() throws XMPPException{
+		if(nonLocalGateways.size()==0){
+			loadNonLocalGateways();
+		}
+		return new ArrayList<Gateway>(nonLocalGateways.values());
+	}
+	
+	/**
+	 * Refreshes the list of gateways offered by remote servers.
+	 * @throws XMPPException
+	 */
+	public void refreshNonLocalGateways() throws XMPPException{
+		loadNonLocalGateways();
+	}
+	
+	/**
+	 * Returns a Gateway object for a given JID. Please note that it is not checked if
+	 * the JID belongs to valid gateway. If this JID doesn't belong to valid gateway
+	 * all operations on this Gateway object should fail with a XMPPException. But there is
+	 * no guarantee for that.
+	 * @param entityJID
+	 * @return a Gateway object
+	 */
+	public Gateway getGateway(String entityJID){
+		if(localGateways.containsKey(entityJID)){
+			return localGateways.get(entityJID);
+		}
+		if(nonLocalGateways.containsKey(entityJID)){
+			return nonLocalGateways.get(entityJID);
+		}
+		if(gateways.containsKey(entityJID)){
+			return gateways.get(entityJID);
+		}
+		Gateway gateway = new Gateway(connection,entityJID);
+		if(entityJID.contains(connection.getHost())){
+			localGateways.put(entityJID, gateway);
+		}
+		else{
+			nonLocalGateways.put(entityJID, gateway);
+		}
+		gateways.put(entityJID, gateway);
+		return gateway;
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/GroupChatInvitation.java b/src/org/jivesoftware/smackx/GroupChatInvitation.java
new file mode 100644
index 0000000..a9ed35e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/GroupChatInvitation.java
@@ -0,0 +1,115 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * A group chat invitation packet extension, which is used to invite other
+ * users to a group chat room. To invite a user to a group chat room, address
+ * a new message to the user and set the room name appropriately, as in the
+ * following code example:
+ *
+ * <pre>
+ * Message message = new Message("user@chat.example.com");
+ * message.setBody("Join me for a group chat!");
+ * message.addExtension(new GroupChatInvitation("room@chat.example.com"););
+ * con.sendPacket(message);
+ * </pre>
+ *
+ * To listen for group chat invitations, use a PacketExtensionFilter for the
+ * <tt>x</tt> element name and <tt>jabber:x:conference</tt> namespace, as in the
+ * following code example:
+ *
+ * <pre>
+ * PacketFilter filter = new PacketExtensionFilter("x", "jabber:x:conference");
+ * // Create a packet collector or packet listeners using the filter...
+ * </pre>
+ *
+ * <b>Note</b>: this protocol is outdated now that the Multi-User Chat (MUC) JEP is available
+ * (<a href="http://www.jabber.org/jeps/jep-0045.html">JEP-45</a>). However, most
+ * existing clients still use this older protocol. Once MUC support becomes more
+ * widespread, this API may be deprecated.
+ * 
+ * @author Matt Tucker
+ */
+public class GroupChatInvitation implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "x";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "jabber:x:conference";
+
+    private String roomAddress;
+
+    /**
+     * Creates a new group chat invitation to the specified room address.
+     * GroupChat room addresses are in the form <tt>room@service</tt>,
+     * where <tt>service</tt> is the name of groupchat server, such as
+     * <tt>chat.example.com</tt>.
+     *
+     * @param roomAddress the address of the group chat room.
+     */
+    public GroupChatInvitation(String roomAddress) {
+        this.roomAddress = roomAddress;
+    }
+
+    /**
+     * Returns the address of the group chat room. GroupChat room addresses
+     * are in the form <tt>room@service</tt>, where <tt>service</tt> is
+     * the name of groupchat server, such as <tt>chat.example.com</tt>.
+     *
+     * @return the address of the group chat room.
+     */
+    public String getRoomAddress() {
+        return roomAddress;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<x xmlns=\"jabber:x:conference\" jid=\"").append(roomAddress).append("\"/>");
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+        public PacketExtension parseExtension (XmlPullParser parser) throws Exception {
+            String roomAddress = parser.getAttributeValue("", "jid");
+            // Advance to end of extension.
+            parser.next();
+            return new GroupChatInvitation(roomAddress);
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/InitStaticCode.java b/src/org/jivesoftware/smackx/InitStaticCode.java
new file mode 100644
index 0000000..12de5af
--- /dev/null
+++ b/src/org/jivesoftware/smackx/InitStaticCode.java
@@ -0,0 +1,51 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import android.content.Context;
+
+/**
+ * Since dalvik on Android does not allow the loading of META-INF files from the
+ * filesystem, the static blocks of some classes have to be inited manually.
+ *
+ * The full list can be found here:
+ * http://fisheye.igniterealtime.org/browse/smack/trunk/build/resources/META-INF/smack-config.xml?hb=true
+ *
+ * @author Florian Schmaus fschmaus@gmail.com
+ *
+ */
+public class InitStaticCode {
+
+    public static void initStaticCode(Context ctx) {
+	    // This has the be the application class loader,
+	    // *not* the system class loader
+	    ClassLoader appClassLoader = ctx.getClassLoader();
+
+	    try {
+		    Class.forName(org.jivesoftware.smackx.ServiceDiscoveryManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smack.PrivacyListManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.XHTMLManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.muc.MultiUserChat.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.filetransfer.FileTransferManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.LastActivityManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smack.ReconnectionManager.class.getName(), true, appClassLoader);
+		    Class.forName(org.jivesoftware.smackx.commands.AdHocCommandManager.class.getName(), true, appClassLoader);
+	    } catch (ClassNotFoundException e) {
+		    throw new IllegalStateException("Could not init static class blocks", e);
+	    }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/LastActivityManager.java b/src/org/jivesoftware/smackx/LastActivityManager.java
new file mode 100644
index 0000000..a9d1f12
--- /dev/null
+++ b/src/org/jivesoftware/smackx/LastActivityManager.java
@@ -0,0 +1,230 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.IQTypeFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.LastActivity;
+
+/**
+ * A last activity manager for handling information about the last activity
+ * associated with a Jabber ID. A manager handles incoming LastActivity requests
+ * of existing Connections. It also allows to request last activity information
+ * of other users.
+ * <p>
+ * 
+ * LastActivity (XEP-0012) based on the sending JID's type allows for retrieval
+ * of:
+ * <ol>
+ * <li>How long a particular user has been idle
+ * <li>How long a particular user has been logged-out and the message the
+ * specified when doing so.
+ * <li>How long a host has been up.
+ * </ol>
+ * <p/>
+ * 
+ * For example to get the idle time of a user logged in a resource, simple send
+ * the LastActivity packet to them, as in the following code:
+ * <p>
+ * 
+ * <pre>
+ * Connection con = new XMPPConnection(&quot;jabber.org&quot;);
+ * con.login(&quot;john&quot;, &quot;doe&quot;);
+ * LastActivity activity = LastActivity.getLastActivity(con, &quot;xray@jabber.org/Smack&quot;);
+ * </pre>
+ * 
+ * To get the lapsed time since the last user logout is the same as above but
+ * with out the resource:
+ * 
+ * <pre>
+ * LastActivity activity = LastActivity.getLastActivity(con, &quot;xray@jabber.org&quot;);
+ * </pre>
+ * 
+ * To get the uptime of a host, you simple send the LastActivity packet to it,
+ * as in the following code example:
+ * <p>
+ * 
+ * <pre>
+ * LastActivity activity = LastActivity.getLastActivity(con, &quot;jabber.org&quot;);
+ * </pre>
+ * 
+ * @author Gabriel Guardincerri
+ * @see <a href="http://xmpp.org/extensions/xep-0012.html">XEP-0012: Last
+ *      Activity</a>
+ */
+
+public class LastActivityManager {
+
+    private long lastMessageSent;
+
+    private Connection connection;
+
+    // Enable the LastActivity support on every established connection
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new LastActivityManager(connection);
+            }
+        });
+    }
+
+    /**
+     * Creates a last activity manager to response last activity requests.
+     * 
+     * @param connection
+     *            The Connection that the last activity requests will use.
+     */
+    private LastActivityManager(Connection connection) {
+        this.connection = connection;
+
+        // Listen to all the sent messages to reset the idle time on each one
+        connection.addPacketSendingListener(new PacketListener() {
+            public void processPacket(Packet packet) {
+                Presence presence = (Presence) packet;
+                Presence.Mode mode = presence.getMode();
+                if (mode == null) return;
+                switch (mode) {
+                case available:
+                case chat:
+                    // We assume that only a switch to available and chat indicates user activity
+                    // since other mode changes could be also a result of some sort of automatism
+                    resetIdleTime();
+                }
+            }
+        }, new PacketTypeFilter(Presence.class));
+
+        connection.addPacketListener(new PacketListener() {
+            @Override
+            public void processPacket(Packet packet) {
+                Message message = (Message) packet;
+                // if it's not an error message, reset the idle time
+                if (message.getType() == Message.Type.error) return;
+                resetIdleTime();
+            }
+        }, new PacketTypeFilter(Message.class));
+
+        // Register a listener for a last activity query
+        connection.addPacketListener(new PacketListener() {
+
+            public void processPacket(Packet packet) {
+                LastActivity message = new LastActivity();
+                message.setType(IQ.Type.RESULT);
+                message.setTo(packet.getFrom());
+                message.setFrom(packet.getTo());
+                message.setPacketID(packet.getPacketID());
+                message.setLastActivity(getIdleTime());
+
+                LastActivityManager.this.connection.sendPacket(message);
+            }
+
+        }, new AndFilter(new IQTypeFilter(IQ.Type.GET), new PacketTypeFilter(LastActivity.class)));
+        ServiceDiscoveryManager.getInstanceFor(connection).addFeature(LastActivity.NAMESPACE);
+        resetIdleTime();
+    }
+
+    /**
+     * Resets the idle time to 0, this should be invoked when a new message is
+     * sent.
+     */
+    private void resetIdleTime() {
+        long now = System.currentTimeMillis();
+        synchronized (this) {
+            lastMessageSent = now;
+        }
+    }
+
+    /**
+     * The idle time is the lapsed time between the last message sent and now.
+     * 
+     * @return the lapsed time between the last message sent and now.
+     */
+    private long getIdleTime() {
+        long lms;
+        long now = System.currentTimeMillis();
+        synchronized (this) {
+            lms = lastMessageSent;
+        }
+        return ((now - lms) / 1000);
+    }
+
+    /**
+     * Returns the last activity of a particular jid. If the jid is a full JID
+     * (i.e., a JID of the form of 'user@host/resource') then the last activity
+     * is the idle time of that connected resource. On the other hand, when the
+     * jid is a bare JID (e.g. 'user@host') then the last activity is the lapsed
+     * time since the last logout or 0 if the user is currently logged in.
+     * Moreover, when the jid is a server or component (e.g., a JID of the form
+     * 'host') the last activity is the uptime.
+     * 
+     * @param con
+     *            the current Connection.
+     * @param jid
+     *            the JID of the user.
+     * @return the LastActivity packet of the jid.
+     * @throws XMPPException
+     *             thrown if a server error has occured.
+     */
+    public static LastActivity getLastActivity(Connection con, String jid) throws XMPPException {
+        LastActivity activity = new LastActivity();
+        activity.setTo(jid);
+
+        PacketCollector collector = con.createPacketCollector(new PacketIDFilter(activity.getPacketID()));
+        con.sendPacket(activity);
+
+        LastActivity response = (LastActivity) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Returns true if Last Activity (XEP-0012) is supported by a given JID
+     * 
+     * @param connection the connection to be used
+     * @param jid a JID to be tested for Last Activity support
+     * @return true if Last Activity is supported, otherwise false
+     */
+    public static boolean isLastActivitySupported(Connection connection, String jid) {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(jid);
+            return result.containsFeature(LastActivity.NAMESPACE);
+        }
+        catch (XMPPException e) {
+            return false;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/MessageEventManager.java b/src/org/jivesoftware/smackx/MessageEventManager.java
new file mode 100644
index 0000000..3502509
--- /dev/null
+++ b/src/org/jivesoftware/smackx/MessageEventManager.java
@@ -0,0 +1,310 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.packet.MessageEvent;
+
+/**
+ * Manages message events requests and notifications. A MessageEventManager provides a high
+ * level access to request for notifications and send event notifications. It also provides 
+ * an easy way to hook up custom logic when requests or notifications are received. 
+ *
+ * @author Gaston Dombiak
+ */
+public class MessageEventManager {
+
+    private List<MessageEventNotificationListener> messageEventNotificationListeners = new ArrayList<MessageEventNotificationListener>();
+    private List<MessageEventRequestListener> messageEventRequestListeners = new ArrayList<MessageEventRequestListener>();
+
+    private Connection con;
+
+    private PacketFilter packetFilter = new PacketExtensionFilter("x", "jabber:x:event");
+    private PacketListener packetListener;
+
+    /**
+     * Creates a new message event manager.
+     *
+     * @param con a Connection to a XMPP server.
+     */
+    public MessageEventManager(Connection con) {
+        this.con = con;
+        init();
+    }
+
+    /**
+     * Adds event notification requests to a message. For each event type that
+     * the user wishes event notifications from the message recepient for, <tt>true</tt>
+     * should be passed in to this method.
+     * 
+     * @param message the message to add the requested notifications.
+     * @param offline specifies if the offline event is requested.
+     * @param delivered specifies if the delivered event is requested.
+     * @param displayed specifies if the displayed event is requested.
+     * @param composing specifies if the composing event is requested.
+     */
+    public static void addNotificationsRequests(Message message, boolean offline,
+            boolean delivered, boolean displayed, boolean composing)
+    {
+        // Create a MessageEvent Package and add it to the message
+        MessageEvent messageEvent = new MessageEvent();
+        messageEvent.setOffline(offline);
+        messageEvent.setDelivered(delivered);
+        messageEvent.setDisplayed(displayed);
+        messageEvent.setComposing(composing);
+        message.addExtension(messageEvent);
+    }
+
+    /**
+     * Adds a message event request listener. The listener will be fired anytime a request for
+     * event notification is received.
+     *
+     * @param messageEventRequestListener a message event request listener.
+     */
+    public void addMessageEventRequestListener(MessageEventRequestListener messageEventRequestListener) {
+        synchronized (messageEventRequestListeners) {
+            if (!messageEventRequestListeners.contains(messageEventRequestListener)) {
+                messageEventRequestListeners.add(messageEventRequestListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a message event request listener. The listener will be fired anytime a request for
+     * event notification is received.
+     *
+     * @param messageEventRequestListener a message event request listener.
+     */
+    public void removeMessageEventRequestListener(MessageEventRequestListener messageEventRequestListener) {
+        synchronized (messageEventRequestListeners) {
+            messageEventRequestListeners.remove(messageEventRequestListener);
+        }
+    }
+
+    /**
+     * Adds a message event notification listener. The listener will be fired anytime a notification
+     * event is received.
+     *
+     * @param messageEventNotificationListener a message event notification listener.
+     */
+    public void addMessageEventNotificationListener(MessageEventNotificationListener messageEventNotificationListener) {
+        synchronized (messageEventNotificationListeners) {
+            if (!messageEventNotificationListeners.contains(messageEventNotificationListener)) {
+                messageEventNotificationListeners.add(messageEventNotificationListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a message event notification listener. The listener will be fired anytime a notification
+     * event is received.
+     *
+     * @param messageEventNotificationListener a message event notification listener.
+     */
+    public void removeMessageEventNotificationListener(MessageEventNotificationListener messageEventNotificationListener) {
+        synchronized (messageEventNotificationListeners) {
+            messageEventNotificationListeners.remove(messageEventNotificationListener);
+        }
+    }
+
+    /**
+     * Fires message event request listeners.
+     */
+    private void fireMessageEventRequestListeners(
+        String from,
+        String packetID,
+        String methodName) {
+        MessageEventRequestListener[] listeners = null;
+        Method method;
+        synchronized (messageEventRequestListeners) {
+            listeners = new MessageEventRequestListener[messageEventRequestListeners.size()];
+            messageEventRequestListeners.toArray(listeners);
+        }
+        try {
+            method =
+                MessageEventRequestListener.class.getDeclaredMethod(
+                    methodName,
+                    new Class[] { String.class, String.class, MessageEventManager.class });
+            for (int i = 0; i < listeners.length; i++) {
+                method.invoke(listeners[i], new Object[] { from, packetID, this });
+            }
+        } catch (NoSuchMethodException e) {
+            e.printStackTrace();
+        } catch (InvocationTargetException e) {
+            e.printStackTrace();
+        } catch (IllegalAccessException e) {
+            e.printStackTrace();
+        }
+    }
+
+    /**
+     * Fires message event notification listeners.
+     */
+    private void fireMessageEventNotificationListeners(
+        String from,
+        String packetID,
+        String methodName) {
+        MessageEventNotificationListener[] listeners = null;
+        Method method;
+        synchronized (messageEventNotificationListeners) {
+            listeners =
+                new MessageEventNotificationListener[messageEventNotificationListeners.size()];
+            messageEventNotificationListeners.toArray(listeners);
+        }
+        try {
+            method =
+                MessageEventNotificationListener.class.getDeclaredMethod(
+                    methodName,
+                    new Class[] { String.class, String.class });
+            for (int i = 0; i < listeners.length; i++) {
+                method.invoke(listeners[i], new Object[] { from, packetID });
+            }
+        } catch (NoSuchMethodException e) {
+            e.printStackTrace();
+        } catch (InvocationTargetException e) {
+            e.printStackTrace();
+        } catch (IllegalAccessException e) {
+            e.printStackTrace();
+        }
+    }
+
+    private void init() {
+        // Listens for all message event packets and fire the proper message event listeners.
+        packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                Message message = (Message) packet;
+                MessageEvent messageEvent =
+                    (MessageEvent) message.getExtension("x", "jabber:x:event");
+                if (messageEvent.isMessageEventRequest()) {
+                    // Fire event for requests of message events
+                    for (Iterator<String> it = messageEvent.getEventTypes(); it.hasNext();)
+                        fireMessageEventRequestListeners(
+                            message.getFrom(),
+                            message.getPacketID(),
+                            it.next().concat("NotificationRequested"));
+                } else
+                    // Fire event for notifications of message events
+                    for (Iterator<String> it = messageEvent.getEventTypes(); it.hasNext();)
+                        fireMessageEventNotificationListeners(
+                            message.getFrom(),
+                            messageEvent.getPacketID(),
+                            it.next().concat("Notification"));
+
+            };
+
+        };
+        con.addPacketListener(packetListener, packetFilter);
+    }
+
+    /**
+     * Sends the notification that the message was delivered to the sender of the original message
+     * 
+     * @param to the recipient of the notification.
+     * @param packetID the id of the message to send.
+     */
+    public void sendDeliveredNotification(String to, String packetID) {
+        // Create the message to send
+        Message msg = new Message(to);
+        // Create a MessageEvent Package and add it to the message
+        MessageEvent messageEvent = new MessageEvent();
+        messageEvent.setDelivered(true);
+        messageEvent.setPacketID(packetID);
+        msg.addExtension(messageEvent);
+        // Send the packet
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Sends the notification that the message was displayed to the sender of the original message
+     * 
+     * @param to the recipient of the notification.
+     * @param packetID the id of the message to send.
+     */
+    public void sendDisplayedNotification(String to, String packetID) {
+        // Create the message to send
+        Message msg = new Message(to);
+        // Create a MessageEvent Package and add it to the message
+        MessageEvent messageEvent = new MessageEvent();
+        messageEvent.setDisplayed(true);
+        messageEvent.setPacketID(packetID);
+        msg.addExtension(messageEvent);
+        // Send the packet
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Sends the notification that the receiver of the message is composing a reply
+     * 
+     * @param to the recipient of the notification.
+     * @param packetID the id of the message to send.
+     */
+    public void sendComposingNotification(String to, String packetID) {
+        // Create the message to send
+        Message msg = new Message(to);
+        // Create a MessageEvent Package and add it to the message
+        MessageEvent messageEvent = new MessageEvent();
+        messageEvent.setComposing(true);
+        messageEvent.setPacketID(packetID);
+        msg.addExtension(messageEvent);
+        // Send the packet
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Sends the notification that the receiver of the message has cancelled composing a reply.
+     * 
+     * @param to the recipient of the notification.
+     * @param packetID the id of the message to send.
+     */
+    public void sendCancelledNotification(String to, String packetID) {
+        // Create the message to send
+        Message msg = new Message(to);
+        // Create a MessageEvent Package and add it to the message
+        MessageEvent messageEvent = new MessageEvent();
+        messageEvent.setCancelled(true);
+        messageEvent.setPacketID(packetID);
+        msg.addExtension(messageEvent);
+        // Send the packet
+        con.sendPacket(msg);
+    }
+
+    public void destroy() {
+        if (con != null) {
+            con.removePacketListener(packetListener);
+        }
+    }
+
+    protected void finalize() throws Throwable {
+        destroy();
+        super.finalize();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/MessageEventNotificationListener.java b/src/org/jivesoftware/smackx/MessageEventNotificationListener.java
new file mode 100644
index 0000000..335dae2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/MessageEventNotificationListener.java
@@ -0,0 +1,74 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+/**
+ *
+ * A listener that is fired anytime a message event notification is received.
+ * Message event notifications are received as a consequence of the request
+ * to receive notifications when sending a message.
+ *
+ * @author Gaston Dombiak
+ */
+public interface MessageEventNotificationListener {
+
+    /**
+     * Called when a notification of message delivered is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     */
+    public void deliveredNotification(String from, String packetID);
+
+    /**
+     * Called when a notification of message displayed is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     */
+    public void displayedNotification(String from, String packetID);
+
+    /**
+     * Called when a notification that the receiver of the message is composing a reply is 
+     * received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     */
+    public void composingNotification(String from, String packetID);
+
+    /**
+     * Called when a notification that the receiver of the message is offline is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     */
+    public void offlineNotification(String from, String packetID);
+
+    /**
+     * Called when a notification that the receiver of the message cancelled the reply 
+     * is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     */
+    public void cancelledNotification(String from, String packetID);
+}
diff --git a/src/org/jivesoftware/smackx/MessageEventRequestListener.java b/src/org/jivesoftware/smackx/MessageEventRequestListener.java
new file mode 100644
index 0000000..86e0808
--- /dev/null
+++ b/src/org/jivesoftware/smackx/MessageEventRequestListener.java
@@ -0,0 +1,86 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+/**
+ *
+ * A listener that is fired anytime a message event request is received.
+ * Message event requests are received when the received message includes an extension 
+ * like this:
+ * 
+ * <pre>
+ * &lt;x xmlns='jabber:x:event'&gt;
+ *  &lt;offline/&gt;
+ *  &lt;delivered/&gt;
+ *  &lt;composing/&gt;
+ * &lt;/x&gt;
+ * </pre>
+ * 
+ * In this example you can see that the sender of the message requests to be notified
+ * when the user couldn't receive the message because he/she is offline, the message 
+ * was delivered or when the receiver of the message is composing a reply. 
+ *
+ * @author Gaston Dombiak
+ */
+public interface MessageEventRequestListener {
+
+    /**
+     * Called when a request for message delivered notification is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     * @param messageEventManager the messageEventManager that fired the listener.
+     */
+    public void deliveredNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager);
+
+    /**
+     * Called when a request for message displayed notification is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     * @param messageEventManager the messageEventManager that fired the listener.
+     */
+    public void displayedNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager);
+
+    /**
+     * Called when a request that the receiver of the message is composing a reply notification is 
+     * received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     * @param messageEventManager the messageEventManager that fired the listener.
+     */
+    public void composingNotificationRequested(String from, String packetID,
+                MessageEventManager messageEventManager);
+
+    /**
+     * Called when a request that the receiver of the message is offline is received.
+     *  
+     * @param from the user that sent the notification.
+     * @param packetID the id of the message that was sent.
+     * @param messageEventManager the messageEventManager that fired the listener.
+     */
+    public void offlineNotificationRequested(String from, String packetID,
+            MessageEventManager messageEventManager);
+
+}
diff --git a/src/org/jivesoftware/smackx/MultipleRecipientInfo.java b/src/org/jivesoftware/smackx/MultipleRecipientInfo.java
new file mode 100644
index 0000000..8738319
--- /dev/null
+++ b/src/org/jivesoftware/smackx/MultipleRecipientInfo.java
@@ -0,0 +1,98 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smackx.packet.MultipleAddresses;
+
+import java.util.List;
+
+/**
+ * MultipleRecipientInfo keeps information about the multiple recipients extension included
+ * in a received packet. Among the information we can find the list of TO and CC addresses.
+ *
+ * @author Gaston Dombiak
+ */
+public class MultipleRecipientInfo {
+
+    MultipleAddresses extension;
+
+    MultipleRecipientInfo(MultipleAddresses extension) {
+        this.extension = extension;
+    }
+
+    /**
+     * Returns the list of {@link org.jivesoftware.smackx.packet.MultipleAddresses.Address}
+     * that were the primary recipients of the packet.
+     *
+     * @return list of primary recipients of the packet.
+     */
+    public List<MultipleAddresses.Address> getTOAddresses() {
+        return extension.getAddressesOfType(MultipleAddresses.TO);
+    }
+
+    /**
+     * Returns the list of {@link org.jivesoftware.smackx.packet.MultipleAddresses.Address}
+     * that were the secondary recipients of the packet.
+     *
+     * @return list of secondary recipients of the packet.
+     */
+    public List<MultipleAddresses.Address> getCCAddresses() {
+        return extension.getAddressesOfType(MultipleAddresses.CC);
+    }
+
+    /**
+     * Returns the JID of a MUC room to which responses should be sent or <tt>null</tt>  if
+     * no specific address was provided. When no specific address was provided then the reply
+     * can be sent to any or all recipients. Otherwise, the user should join the specified room
+     * and send the reply to the room.
+     *
+     * @return the JID of a MUC room to which responses should be sent or <tt>null</tt>  if
+     *         no specific address was provided.
+     */
+    public String getReplyRoom() {
+        List<MultipleAddresses.Address> replyRoom = extension.getAddressesOfType(MultipleAddresses.REPLY_ROOM);
+        return replyRoom.isEmpty() ? null : ((MultipleAddresses.Address) replyRoom.get(0)).getJid();
+    }
+
+    /**
+     * Returns true if the received packet should not be replied. Use
+     * {@link MultipleRecipientManager#reply(org.jivesoftware.smack.Connection, org.jivesoftware.smack.packet.Message, org.jivesoftware.smack.packet.Message)}
+     * to send replies. 
+     *
+     * @return true if the received packet should not be replied.
+     */
+    public boolean shouldNotReply() {
+        return !extension.getAddressesOfType(MultipleAddresses.NO_REPLY).isEmpty();
+    }
+
+    /**
+     * Returns the address to which all replies are requested to be sent or <tt>null</tt> if
+     * no specific address was provided. When no specific address was provided then the reply
+     * can be sent to any or all recipients.
+     *
+     * @return the address to which all replies are requested to be sent or <tt>null</tt> if
+     *         no specific address was provided.
+     */
+    public MultipleAddresses.Address getReplyAddress() {
+        List<MultipleAddresses.Address> replyTo = extension.getAddressesOfType(MultipleAddresses.REPLY_TO);
+        return replyTo.isEmpty() ? null : (MultipleAddresses.Address) replyTo.get(0);
+    }
+}
diff --git a/src/org/jivesoftware/smackx/MultipleRecipientManager.java b/src/org/jivesoftware/smackx/MultipleRecipientManager.java
new file mode 100644
index 0000000..83aface
--- /dev/null
+++ b/src/org/jivesoftware/smackx/MultipleRecipientManager.java
@@ -0,0 +1,353 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.Cache;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.MultipleAddresses;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * A MultipleRecipientManager allows to send packets to multiple recipients by making use of
+ * <a href="http://www.jabber.org/jeps/jep-0033.html">JEP-33: Extended Stanza Addressing</a>.
+ * It also allows to send replies to packets that were sent to multiple recipients.
+ *
+ * @author Gaston Dombiak
+ */
+public class MultipleRecipientManager {
+
+    /**
+     * Create a cache to hold the 100 most recently accessed elements for a period of
+     * 24 hours.
+     */
+    private static Cache<String, String> services = new Cache<String, String>(100, 24 * 60 * 60 * 1000);
+
+    /**
+     * Sends the specified packet to the list of specified recipients using the
+     * specified connection. If the server has support for JEP-33 then only one
+     * packet is going to be sent to the server with the multiple recipient instructions.
+     * However, if JEP-33 is not supported by the server then the client is going to send
+     * the packet to each recipient.
+     *
+     * @param connection the connection to use to send the packet.
+     * @param packet     the packet to send to the list of recipients.
+     * @param to         the list of JIDs to include in the TO list or <tt>null</tt> if no TO
+     *                   list exists.
+     * @param cc         the list of JIDs to include in the CC list or <tt>null</tt> if no CC
+     *                   list exists.
+     * @param bcc        the list of JIDs to include in the BCC list or <tt>null</tt> if no BCC
+     *                   list exists.
+     * @throws XMPPException if server does not support JEP-33: Extended Stanza Addressing and
+     *                       some JEP-33 specific features were requested.
+     */
+    public static void send(Connection connection, Packet packet, List<String> to, List<String> cc, List<String> bcc)
+            throws XMPPException {
+        send(connection, packet, to, cc, bcc, null, null, false);
+    }
+
+    /**
+     * Sends the specified packet to the list of specified recipients using the
+     * specified connection. If the server has support for JEP-33 then only one
+     * packet is going to be sent to the server with the multiple recipient instructions.
+     * However, if JEP-33 is not supported by the server then the client is going to send
+     * the packet to each recipient.
+     *
+     * @param connection the connection to use to send the packet.
+     * @param packet     the packet to send to the list of recipients.
+     * @param to         the list of JIDs to include in the TO list or <tt>null</tt> if no TO
+     *                   list exists.
+     * @param cc         the list of JIDs to include in the CC list or <tt>null</tt> if no CC
+     *                   list exists.
+     * @param bcc        the list of JIDs to include in the BCC list or <tt>null</tt> if no BCC
+     *                   list exists.
+     * @param replyTo    address to which all replies are requested to be sent or <tt>null</tt>
+     *                   indicating that they can reply to any address.
+     * @param replyRoom  JID of a MUC room to which responses should be sent or <tt>null</tt>
+     *                   indicating that they can reply to any address.
+     * @param noReply    true means that receivers should not reply to the message.
+     * @throws XMPPException if server does not support JEP-33: Extended Stanza Addressing and
+     *                       some JEP-33 specific features were requested.
+     */
+    public static void send(Connection connection, Packet packet, List<String> to, List<String> cc, List<String> bcc,
+            String replyTo, String replyRoom, boolean noReply) throws XMPPException {
+        String serviceAddress = getMultipleRecipienServiceAddress(connection);
+        if (serviceAddress != null) {
+            // Send packet to target users using multiple recipient service provided by the server
+            sendThroughService(connection, packet, to, cc, bcc, replyTo, replyRoom, noReply,
+                    serviceAddress);
+        }
+        else {
+            // Server does not support JEP-33 so try to send the packet to each recipient
+            if (noReply || (replyTo != null && replyTo.trim().length() > 0) ||
+                    (replyRoom != null && replyRoom.trim().length() > 0)) {
+                // Some specified JEP-33 features were requested so throw an exception alerting
+                // the user that this features are not available
+                throw new XMPPException("Extended Stanza Addressing not supported by server");
+            }
+            // Send the packet to each individual recipient
+            sendToIndividualRecipients(connection, packet, to, cc, bcc);
+        }
+    }
+
+    /**
+     * Sends a reply to a previously received packet that was sent to multiple recipients. Before
+     * attempting to send the reply message some checkings are performed. If any of those checkings
+     * fail then an XMPPException is going to be thrown with the specific error detail.
+     *
+     * @param connection the connection to use to send the reply.
+     * @param original   the previously received packet that was sent to multiple recipients.
+     * @param reply      the new message to send as a reply.
+     * @throws XMPPException if the original message was not sent to multiple recipients, or the
+     *                       original message cannot be replied or reply should be sent to a room.
+     */
+    public static void reply(Connection connection, Message original, Message reply)
+            throws XMPPException {
+        MultipleRecipientInfo info = getMultipleRecipientInfo(original);
+        if (info == null) {
+            throw new XMPPException("Original message does not contain multiple recipient info");
+        }
+        if (info.shouldNotReply()) {
+            throw new XMPPException("Original message should not be replied");
+        }
+        if (info.getReplyRoom() != null) {
+            throw new XMPPException("Reply should be sent through a room");
+        }
+        // Any <thread/> element from the initial message MUST be copied into the reply.
+        if (original.getThread() != null) {
+            reply.setThread(original.getThread());
+        }
+        MultipleAddresses.Address replyAddress = info.getReplyAddress();
+        if (replyAddress != null && replyAddress.getJid() != null) {
+            // Send reply to the reply_to address
+            reply.setTo(replyAddress.getJid());
+            connection.sendPacket(reply);
+        }
+        else {
+            // Send reply to multiple recipients
+            List<String> to = new ArrayList<String>();
+            List<String> cc = new ArrayList<String>();
+            for (Iterator<MultipleAddresses.Address> it = info.getTOAddresses().iterator(); it.hasNext();) {
+                String jid = it.next().getJid();
+                to.add(jid);
+            }
+            for (Iterator<MultipleAddresses.Address> it = info.getCCAddresses().iterator(); it.hasNext();) {
+                String jid = it.next().getJid();
+                cc.add(jid);
+            }
+            // Add original sender as a 'to' address (if not already present)
+            if (!to.contains(original.getFrom()) && !cc.contains(original.getFrom())) {
+                to.add(original.getFrom());
+            }
+            // Remove the sender from the TO/CC list (try with bare JID too)
+            String from = connection.getUser();
+            if (!to.remove(from) && !cc.remove(from)) {
+                String bareJID = StringUtils.parseBareAddress(from);
+                to.remove(bareJID);
+                cc.remove(bareJID);
+            }
+
+            String serviceAddress = getMultipleRecipienServiceAddress(connection);
+            if (serviceAddress != null) {
+                // Send packet to target users using multiple recipient service provided by the server
+                sendThroughService(connection, reply, to, cc, null, null, null, false,
+                        serviceAddress);
+            }
+            else {
+                // Server does not support JEP-33 so try to send the packet to each recipient
+                sendToIndividualRecipients(connection, reply, to, cc, null);
+            }
+        }
+    }
+
+    /**
+     * Returns the {@link MultipleRecipientInfo} contained in the specified packet or
+     * <tt>null</tt> if none was found. Only packets sent to multiple recipients will
+     * contain such information.
+     *
+     * @param packet the packet to check.
+     * @return the MultipleRecipientInfo contained in the specified packet or <tt>null</tt>
+     *         if none was found.
+     */
+    public static MultipleRecipientInfo getMultipleRecipientInfo(Packet packet) {
+        MultipleAddresses extension = (MultipleAddresses) packet
+                .getExtension("addresses", "http://jabber.org/protocol/address");
+        return extension == null ? null : new MultipleRecipientInfo(extension);
+    }
+
+    private static void sendToIndividualRecipients(Connection connection, Packet packet,
+            List<String> to, List<String> cc, List<String> bcc) {
+        if (to != null) {
+            for (Iterator<String> it = to.iterator(); it.hasNext();) {
+                String jid = it.next();
+                packet.setTo(jid);
+                connection.sendPacket(new PacketCopy(packet.toXML()));
+            }
+        }
+        if (cc != null) {
+            for (Iterator<String> it = cc.iterator(); it.hasNext();) {
+                String jid = it.next();
+                packet.setTo(jid);
+                connection.sendPacket(new PacketCopy(packet.toXML()));
+            }
+        }
+        if (bcc != null) {
+            for (Iterator<String> it = bcc.iterator(); it.hasNext();) {
+                String jid = it.next();
+                packet.setTo(jid);
+                connection.sendPacket(new PacketCopy(packet.toXML()));
+            }
+        }
+    }
+
+    private static void sendThroughService(Connection connection, Packet packet, List<String> to,
+            List<String> cc, List<String> bcc, String replyTo, String replyRoom, boolean noReply,
+            String serviceAddress) {
+        // Create multiple recipient extension
+        MultipleAddresses multipleAddresses = new MultipleAddresses();
+        if (to != null) {
+            for (Iterator<String> it = to.iterator(); it.hasNext();) {
+                String jid = it.next();
+                multipleAddresses.addAddress(MultipleAddresses.TO, jid, null, null, false, null);
+            }
+        }
+        if (cc != null) {
+            for (Iterator<String> it = cc.iterator(); it.hasNext();) {
+                String jid = it.next();
+                multipleAddresses.addAddress(MultipleAddresses.CC, jid, null, null, false, null);
+            }
+        }
+        if (bcc != null) {
+            for (Iterator<String> it = bcc.iterator(); it.hasNext();) {
+                String jid = it.next();
+                multipleAddresses.addAddress(MultipleAddresses.BCC, jid, null, null, false, null);
+            }
+        }
+        if (noReply) {
+            multipleAddresses.setNoReply();
+        }
+        else {
+            if (replyTo != null && replyTo.trim().length() > 0) {
+                multipleAddresses
+                        .addAddress(MultipleAddresses.REPLY_TO, replyTo, null, null, false, null);
+            }
+            if (replyRoom != null && replyRoom.trim().length() > 0) {
+                multipleAddresses.addAddress(MultipleAddresses.REPLY_ROOM, replyRoom, null, null,
+                        false, null);
+            }
+        }
+        // Set the multiple recipient service address as the target address
+        packet.setTo(serviceAddress);
+        // Add extension to packet
+        packet.addExtension(multipleAddresses);
+        // Send the packet
+        connection.sendPacket(packet);
+    }
+
+    /**
+     * Returns the address of the multiple recipients service. To obtain such address service
+     * discovery is going to be used on the connected server and if none was found then another
+     * attempt will be tried on the server items. The discovered information is going to be
+     * cached for 24 hours.
+     *
+     * @param connection the connection to use for disco. The connected server is going to be
+     *                   queried.
+     * @return the address of the multiple recipients service or <tt>null</tt> if none was found.
+     */
+    private static String getMultipleRecipienServiceAddress(Connection connection) {
+        String serviceName = connection.getServiceName();
+        String serviceAddress = (String) services.get(serviceName);
+        if (serviceAddress == null) {
+            synchronized (services) {
+                serviceAddress = (String) services.get(serviceName);
+                if (serviceAddress == null) {
+
+                    // Send the disco packet to the server itself
+                    try {
+                        DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection)
+                                .discoverInfo(serviceName);
+                        // Check if the server supports JEP-33
+                        if (info.containsFeature("http://jabber.org/protocol/address")) {
+                            serviceAddress = serviceName;
+                        }
+                        else {
+                            // Get the disco items and send the disco packet to each server item
+                            DiscoverItems items = ServiceDiscoveryManager.getInstanceFor(connection)
+                                    .discoverItems(serviceName);
+                            for (Iterator<DiscoverItems.Item> it = items.getItems(); it.hasNext();) {
+                                DiscoverItems.Item item = it.next();
+                                info = ServiceDiscoveryManager.getInstanceFor(connection)
+                                        .discoverInfo(item.getEntityID(), item.getNode());
+                                if (info.containsFeature("http://jabber.org/protocol/address")) {
+                                    serviceAddress = serviceName;
+                                    break;
+                                }
+                            }
+
+                        }
+                        // Cache the discovered information
+                        services.put(serviceName, serviceAddress == null ? "" : serviceAddress);
+                    }
+                    catch (XMPPException e) {
+                        e.printStackTrace();
+                    }
+                }
+            }
+        }
+
+        return "".equals(serviceAddress) ? null : serviceAddress;
+    }
+
+    /**
+     * Packet that holds the XML stanza to send. This class is useful when the same packet
+     * is needed to be sent to different recipients. Since using the same packet is not possible
+     * (i.e. cannot change the TO address of a queues packet to be sent) then this class was
+     * created to keep the XML stanza to send.
+     */
+    private static class PacketCopy extends Packet {
+
+        private String text;
+
+        /**
+         * Create a copy of a packet with the text to send. The passed text must be a valid text to
+         * send to the server, no validation will be done on the passed text.
+         *
+         * @param text the whole text of the packet to send
+         */
+        public PacketCopy(String text) {
+            this.text = text;
+        }
+
+        public String toXML() {
+            return text;
+        }
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/NodeInformationProvider.java b/src/org/jivesoftware/smackx/NodeInformationProvider.java
new file mode 100644
index 0000000..27ee53a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/NodeInformationProvider.java
@@ -0,0 +1,75 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+
+import java.util.List;
+
+
+/**
+ * The NodeInformationProvider is responsible for providing supported indentities, features
+ * and hosted items (i.e. DiscoverItems.Item) about a given node. This information will be
+ * requested each time this XMPPP client receives a disco info or items requests on the
+ * given node. each time this XMPPP client receives a disco info or items requests on the
+ * given node.
+ *
+ * @author Gaston Dombiak
+ */
+public interface NodeInformationProvider {
+
+    /**
+     * Returns a list of the Items {@link org.jivesoftware.smackx.packet.DiscoverItems.Item}
+     * defined in the node. For example, the MUC protocol specifies that an XMPP client should 
+     * answer an Item for each joined room when asked for the rooms where the use has joined.
+     *  
+     * @return a list of the Items defined in the node.
+     */
+    List<DiscoverItems.Item> getNodeItems();
+
+    /**
+     * Returns a list of the features defined in the node. For
+     * example, the entity caps protocol specifies that an XMPP client
+     * should answer with each feature supported by the client version
+     * or extension.
+     *
+     * @return a list of the feature strings defined in the node.
+     */
+    List<String> getNodeFeatures();
+
+    /**
+     * Returns a list of the indentites defined in the node. For
+     * example, the x-command protocol must provide an identity of
+     * category automation and type command-node for each command.
+     *
+     * @return a list of the Identities defined in the node.
+     */
+    List<DiscoverInfo.Identity> getNodeIdentities();
+
+    /**
+     * Returns a list of the packet extensions defined in the node.
+     *
+     * @return a list of the packet extensions defined in the node.
+     */
+    List<PacketExtension> getNodePacketExtensions();
+}
diff --git a/src/org/jivesoftware/smackx/OfflineMessageHeader.java b/src/org/jivesoftware/smackx/OfflineMessageHeader.java
new file mode 100644
index 0000000..55fd149
--- /dev/null
+++ b/src/org/jivesoftware/smackx/OfflineMessageHeader.java
@@ -0,0 +1,85 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smackx.packet.DiscoverItems;
+
+/**
+ * The OfflineMessageHeader holds header information of an offline message. The header
+ * information was retrieved using the {@link OfflineMessageManager} class.<p>
+ *
+ * Each offline message is identified by the target user of the offline message and a unique stamp.
+ * Use {@link OfflineMessageManager#getMessages(java.util.List)} to retrieve the whole message.
+ *
+ * @author Gaston Dombiak
+ */
+public class OfflineMessageHeader {
+    /**
+     * Bare JID of the user that was offline when the message was sent.
+     */
+    private String user;
+    /**
+     * Full JID of the user that sent the message.
+     */
+    private String jid;
+    /**
+     * Stamp that uniquely identifies the offline message. This stamp will be used for
+     * getting the specific message or delete it. The stamp may be of the form UTC timestamps
+     * but it is not required to have that format.
+     */
+    private String stamp;
+
+    public OfflineMessageHeader(DiscoverItems.Item item) {
+        super();
+        user = item.getEntityID();
+        jid = item.getName();
+        stamp = item.getNode();
+    }
+
+    /**
+     * Returns the bare JID of the user that was offline when the message was sent.
+     *
+     * @return the bare JID of the user that was offline when the message was sent.
+     */
+    public String getUser() {
+        return user;
+    }
+
+    /**
+     * Returns the full JID of the user that sent the message.
+     *
+     * @return the full JID of the user that sent the message.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Returns the stamp that uniquely identifies the offline message. This stamp will
+     * be used for getting the specific message or delete it. The stamp may be of the
+     * form UTC timestamps but it is not required to have that format.
+     *
+     * @return the stamp that uniquely identifies the offline message.
+     */
+    public String getStamp() {
+        return stamp;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/OfflineMessageManager.java b/src/org/jivesoftware/smackx/OfflineMessageManager.java
new file mode 100644
index 0000000..dbe889d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/OfflineMessageManager.java
@@ -0,0 +1,284 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.*;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.OfflineMessageInfo;
+import org.jivesoftware.smackx.packet.OfflineMessageRequest;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * The OfflineMessageManager helps manage offline messages even before the user has sent an
+ * available presence. When a user asks for his offline messages before sending an available
+ * presence then the server will not send a flood with all the offline messages when the user
+ * becomes online. The server will not send a flood with all the offline messages to the session
+ * that made the offline messages request or to any other session used by the user that becomes
+ * online.<p>
+ *
+ * Once the session that made the offline messages request has been closed and the user becomes
+ * offline in all the resources then the server will resume storing the messages offline and will
+ * send all the offline messages to the user when he becomes online. Therefore, the server will
+ * flood the user when he becomes online unless the user uses this class to manage his offline
+ * messages.
+ *
+ * @author Gaston Dombiak
+ */
+public class OfflineMessageManager {
+
+    private final static String namespace = "http://jabber.org/protocol/offline";
+
+    private Connection connection;
+
+    private PacketFilter packetFilter;
+
+    public OfflineMessageManager(Connection connection) {
+        this.connection = connection;
+        packetFilter =
+                new AndFilter(new PacketExtensionFilter("offline", namespace),
+                        new PacketTypeFilter(Message.class));
+    }
+
+    /**
+     * Returns true if the server supports Flexible Offline Message Retrieval. When the server
+     * supports Flexible Offline Message Retrieval it is possible to get the header of the offline
+     * messages, get specific messages, delete specific messages, etc.
+     *
+     * @return a boolean indicating if the server supports Flexible Offline Message Retrieval.
+     * @throws XMPPException If the user is not allowed to make this request.
+     */
+    public boolean supportsFlexibleRetrieval() throws XMPPException {
+        DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(connection.getServiceName());
+        return info.containsFeature(namespace);
+    }
+
+    /**
+     * Returns the number of offline messages for the user of the connection.
+     *
+     * @return the number of offline messages for the user of the connection.
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public int getMessageCount() throws XMPPException {
+        DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(null,
+                namespace);
+        Form extendedInfo = Form.getFormFrom(info);
+        if (extendedInfo != null) {
+            String value = extendedInfo.getField("number_of_messages").getValues().next();
+            return Integer.parseInt(value);
+        }
+        return 0;
+    }
+
+    /**
+     * Returns an iterator on <tt>OfflineMessageHeader</tt> that keep information about the
+     * offline message. The OfflineMessageHeader includes a stamp that could be used to retrieve
+     * the complete message or delete the specific message.
+     *
+     * @return an iterator on <tt>OfflineMessageHeader</tt> that keep information about the offline
+     *         message.
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public Iterator<OfflineMessageHeader> getHeaders() throws XMPPException {
+        List<OfflineMessageHeader> answer = new ArrayList<OfflineMessageHeader>();
+        DiscoverItems items = ServiceDiscoveryManager.getInstanceFor(connection).discoverItems(
+                null, namespace);
+        for (Iterator<DiscoverItems.Item> it = items.getItems(); it.hasNext();) {
+            DiscoverItems.Item item = it.next();
+            answer.add(new OfflineMessageHeader(item));
+        }
+        return answer.iterator();
+    }
+
+    /**
+     * Returns an Iterator with the offline <tt>Messages</tt> whose stamp matches the specified
+     * request. The request will include the list of stamps that uniquely identifies
+     * the offline messages to retrieve. The returned offline messages will not be deleted
+     * from the server. Use {@link #deleteMessages(java.util.List)} to delete the messages.
+     *
+     * @param nodes the list of stamps that uniquely identifies offline message.
+     * @return an Iterator with the offline <tt>Messages</tt> that were received as part of
+     *         this request.
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public Iterator<Message> getMessages(final List<String> nodes) throws XMPPException {
+        List<Message> messages = new ArrayList<Message>();
+        OfflineMessageRequest request = new OfflineMessageRequest();
+        for (String node : nodes) {
+            OfflineMessageRequest.Item item = new OfflineMessageRequest.Item(node);
+            item.setAction("view");
+            request.addItem(item);
+        }
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(request.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Filter offline messages that were requested by this request
+        PacketFilter messageFilter = new AndFilter(packetFilter, new PacketFilter() {
+            public boolean accept(Packet packet) {
+                OfflineMessageInfo info = (OfflineMessageInfo) packet.getExtension("offline",
+                        namespace);
+                return nodes.contains(info.getNode());
+            }
+        });
+        PacketCollector messageCollector = connection.createPacketCollector(messageFilter);
+        // Send the retrieval request to the server.
+        connection.sendPacket(request);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        } else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+
+        // Collect the received offline messages
+        Message message = (Message) messageCollector.nextResult(
+                SmackConfiguration.getPacketReplyTimeout());
+        while (message != null) {
+            messages.add(message);
+            message =
+                    (Message) messageCollector.nextResult(
+                            SmackConfiguration.getPacketReplyTimeout());
+        }
+        // Stop queuing offline messages
+        messageCollector.cancel();
+        return messages.iterator();
+    }
+
+    /**
+     * Returns an Iterator with all the offline <tt>Messages</tt> of the user. The returned offline
+     * messages will not be deleted from the server. Use {@link #deleteMessages(java.util.List)}
+     * to delete the messages.
+     *
+     * @return an Iterator with all the offline <tt>Messages</tt> of the user.
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public Iterator<Message> getMessages() throws XMPPException {
+        List<Message> messages = new ArrayList<Message>();
+        OfflineMessageRequest request = new OfflineMessageRequest();
+        request.setFetch(true);
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(request.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Filter offline messages that were requested by this request
+        PacketCollector messageCollector = connection.createPacketCollector(packetFilter);
+        // Send the retrieval request to the server.
+        connection.sendPacket(request);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        } else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+
+        // Collect the received offline messages
+        Message message = (Message) messageCollector.nextResult(
+                SmackConfiguration.getPacketReplyTimeout());
+        while (message != null) {
+            messages.add(message);
+            message =
+                    (Message) messageCollector.nextResult(
+                            SmackConfiguration.getPacketReplyTimeout());
+        }
+        // Stop queuing offline messages
+        messageCollector.cancel();
+        return messages.iterator();
+    }
+
+    /**
+     * Deletes the specified list of offline messages. The request will include the list of
+     * stamps that uniquely identifies the offline messages to delete.
+     *
+     * @param nodes the list of stamps that uniquely identifies offline message.
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public void deleteMessages(List<String> nodes) throws XMPPException {
+        OfflineMessageRequest request = new OfflineMessageRequest();
+        for (String node : nodes) {
+            OfflineMessageRequest.Item item = new OfflineMessageRequest.Item(node);
+            item.setAction("remove");
+            request.addItem(item);
+        }
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(request.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the deletion request to the server.
+        connection.sendPacket(request);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        } else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    /**
+     * Deletes all offline messages of the user.
+     *
+     * @throws XMPPException If the user is not allowed to make this request or the server does
+     *                       not support offline message retrieval.
+     */
+    public void deleteMessages() throws XMPPException {
+        OfflineMessageRequest request = new OfflineMessageRequest();
+        request.setPurge(true);
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(request.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the deletion request to the server.
+        connection.sendPacket(request);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        } else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/PEPListener.java b/src/org/jivesoftware/smackx/PEPListener.java
new file mode 100644
index 0000000..1d39484
--- /dev/null
+++ b/src/org/jivesoftware/smackx/PEPListener.java
@@ -0,0 +1,42 @@
+/**
+ * $RCSfile: PEPListener.java,v $
+ * $Revision: 1.1 $
+ * $Date: 2007/11/03 00:14:32 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smackx.packet.PEPEvent;
+
+
+/**
+ *
+ * A listener that is fired anytime a PEP event message is received.
+ *
+ * @author Jeff Williams
+ */
+public interface PEPListener {
+
+    /**
+     * Called when PEP events are received as part of a presence subscribe or message filter.
+     *  
+     * @param from the user that sent the entries.
+     * @param event the event contained in the message.
+     */
+    public void eventReceived(String from, PEPEvent event);
+
+}
diff --git a/src/org/jivesoftware/smackx/PEPManager.java b/src/org/jivesoftware/smackx/PEPManager.java
new file mode 100644
index 0000000..857f1c4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/PEPManager.java
@@ -0,0 +1,160 @@
+/**
+ * $RCSfile: PEPManager.java,v $
+ * $Revision: 1.4 $
+ * $Date: 2007/11/06 21:43:40 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.IQ.Type;
+import org.jivesoftware.smackx.packet.PEPEvent;
+import org.jivesoftware.smackx.packet.PEPItem;
+import org.jivesoftware.smackx.packet.PEPPubSub;
+
+/**
+ *
+ * Manages Personal Event Publishing (XEP-163). A PEPManager provides a high level access to
+ * pubsub personal events. It also provides an easy way
+ * to hook up custom logic when events are received from another XMPP client through PEPListeners.
+ * 
+ * Use example:
+ * 
+ * <pre>
+ *   PEPManager pepManager = new PEPManager(smackConnection);
+ *   pepManager.addPEPListener(new PEPListener() {
+ *       public void eventReceived(String inFrom, PEPEvent inEvent) {
+ *           LOGGER.debug("Event received: " + inEvent);
+ *       }
+ *   });
+ *
+ *   PEPProvider pepProvider = new PEPProvider();
+ *   pepProvider.registerPEPParserExtension("http://jabber.org/protocol/tune", new TuneProvider());
+ *   ProviderManager.getInstance().addExtensionProvider("event", "http://jabber.org/protocol/pubsub#event", pepProvider);
+ *   
+ *   Tune tune = new Tune("jeff", "1", "CD", "My Title", "My Track");
+ *   pepManager.publish(tune);
+ * </pre>
+ * 
+ * @author Jeff Williams
+ */
+public class PEPManager {
+
+    private List<PEPListener> pepListeners = new ArrayList<PEPListener>();
+
+    private Connection connection;
+
+    private PacketFilter packetFilter = new PacketExtensionFilter("event", "http://jabber.org/protocol/pubsub#event");
+    private PacketListener packetListener;
+
+    /**
+     * Creates a new PEP exchange manager.
+     *
+     * @param connection a Connection which is used to send and receive messages.
+     */
+    public PEPManager(Connection connection) {
+        this.connection = connection;
+        init();
+    }
+
+    /**
+     * Adds a listener to PEPs. The listener will be fired anytime PEP events
+     * are received from remote XMPP clients.
+     *
+     * @param pepListener a roster exchange listener.
+     */
+    public void addPEPListener(PEPListener pepListener) {
+        synchronized (pepListeners) {
+            if (!pepListeners.contains(pepListener)) {
+                pepListeners.add(pepListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener from PEP events.
+     *
+     * @param pepListener a roster exchange listener.
+     */
+    public void removePEPListener(PEPListener pepListener) {
+        synchronized (pepListeners) {
+            pepListeners.remove(pepListener);
+        }
+    }
+
+    /**
+     * Publish an event.
+     * 
+     * @param item the item to publish.
+     */
+    public void publish(PEPItem item) {
+        // Create a new message to publish the event.
+        PEPPubSub pubSub = new PEPPubSub(item);
+        pubSub.setType(Type.SET);
+        //pubSub.setFrom(connection.getUser());
+ 
+        // Send the message that contains the roster
+        connection.sendPacket(pubSub);
+    }
+
+    /**
+     * Fires roster exchange listeners.
+     */
+    private void firePEPListeners(String from, PEPEvent event) {
+        PEPListener[] listeners = null;
+        synchronized (pepListeners) {
+            listeners = new PEPListener[pepListeners.size()];
+            pepListeners.toArray(listeners);
+        }
+        for (int i = 0; i < listeners.length; i++) {
+            listeners[i].eventReceived(from, event);
+        }
+    }
+
+    private void init() {
+        // Listens for all roster exchange packets and fire the roster exchange listeners.
+        packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                Message message = (Message) packet;
+                PEPEvent event = (PEPEvent) message.getExtension("event", "http://jabber.org/protocol/pubsub#event");
+                // Fire event for roster exchange listeners
+                firePEPListeners(message.getFrom(), event);
+            };
+
+        };
+        connection.addPacketListener(packetListener, packetFilter);
+    }
+
+    public void destroy() {
+        if (connection != null)
+            connection.removePacketListener(packetListener);
+
+    }
+
+    protected void finalize() throws Throwable {
+        destroy();
+        super.finalize();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/PrivateDataManager.java b/src/org/jivesoftware/smackx/PrivateDataManager.java
new file mode 100644
index 0000000..c6440bc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/PrivateDataManager.java
@@ -0,0 +1,359 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.packet.DefaultPrivateData;
+import org.jivesoftware.smackx.packet.PrivateData;
+import org.jivesoftware.smackx.provider.PrivateDataProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.Hashtable;
+import java.util.Map;
+
+/**
+ * Manages private data, which is a mechanism to allow users to store arbitrary XML
+ * data on an XMPP server. Each private data chunk is defined by a element name and
+ * XML namespace. Example private data:
+ *
+ * <pre>
+ * &lt;color xmlns="http://example.com/xmpp/color"&gt;
+ *     &lt;favorite&gt;blue&lt;/blue&gt;
+ *     &lt;leastFavorite&gt;puce&lt;/leastFavorite&gt;
+ * &lt;/color&gt;
+ * </pre>
+ *
+ * {@link PrivateDataProvider} instances are responsible for translating the XML into objects.
+ * If no PrivateDataProvider is registered for a given element name and namespace, then
+ * a {@link DefaultPrivateData} instance will be returned.<p>
+ *
+ * Warning: this is an non-standard protocol documented by
+ * <a href="http://www.jabber.org/jeps/jep-0049.html">JEP-49</a>. Because this is a
+ * non-standard protocol, it is subject to change.
+ *
+ * @author Matt Tucker
+ */
+public class PrivateDataManager {
+
+    /**
+     * Map of provider instances.
+     */
+    private static Map<String, PrivateDataProvider> privateDataProviders = new Hashtable<String, PrivateDataProvider>();
+
+    /**
+     * Returns the private data provider registered to the specified XML element name and namespace.
+     * For example, if a provider was registered to the element name "prefs" and the
+     * namespace "http://www.xmppclient.com/prefs", then the following packet would trigger
+     * the provider:
+     *
+     * <pre>
+     * &lt;iq type='result' to='joe@example.com' from='mary@example.com' id='time_1'&gt;
+     *     &lt;query xmlns='jabber:iq:private'&gt;
+     *         &lt;prefs xmlns='http://www.xmppclient.com/prefs'&gt;
+     *             &lt;value1&gt;ABC&lt;/value1&gt;
+     *             &lt;value2&gt;XYZ&lt;/value2&gt;
+     *         &lt;/prefs&gt;
+     *     &lt;/query&gt;
+     * &lt;/iq&gt;</pre>
+     *
+     * <p>Note: this method is generally only called by the internal Smack classes.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     * @return the PrivateData provider.
+     */
+    public static PrivateDataProvider getPrivateDataProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        return (PrivateDataProvider)privateDataProviders.get(key);
+    }
+
+    /**
+     * Adds a private data provider with the specified element name and name space. The provider
+     * will override any providers loaded through the classpath.
+     *
+     * @param elementName the XML element name.
+     * @param namespace the XML namespace.
+     * @param provider the private data provider.
+     */
+    public static void addPrivateDataProvider(String elementName, String namespace,
+            PrivateDataProvider provider)
+    {
+        String key = getProviderKey(elementName, namespace);
+        privateDataProviders.put(key, provider);
+    }
+
+    /**
+     * Removes a private data provider with the specified element name and namespace.
+     *
+     * @param elementName The XML element name.
+     * @param namespace The XML namespace.
+     */
+    public static void removePrivateDataProvider(String elementName, String namespace) {
+        String key = getProviderKey(elementName, namespace);
+        privateDataProviders.remove(key);
+    }
+
+
+    private Connection connection;
+
+    /**
+     * The user to get and set private data for. In most cases, this value should
+     * be <tt>null</tt>, as the typical use of private data is to get and set
+     * your own private data and not others.
+     */
+    private String user;
+
+    /**
+     * Creates a new private data manager. The connection must have
+     * undergone a successful login before being used to construct an instance of
+     * this class.
+     *
+     * @param connection an XMPP connection which must have already undergone a
+     *      successful login.
+     */
+    public PrivateDataManager(Connection connection) {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Must be logged in to XMPP server.");
+        }
+        this.connection = connection;
+    }
+
+    /**
+     * Creates a new private data manager for a specific user (special case). Most
+     * servers only support getting and setting private data for the user that
+     * authenticated via the connection. However, some servers support the ability
+     * to get and set private data for other users (for example, if you are the
+     * administrator). The connection must have undergone a successful login before
+     * being used to construct an instance of this class.
+     *
+     * @param connection an XMPP connection which must have already undergone a
+     *      successful login.
+     * @param user the XMPP address of the user to get and set private data for.
+     */
+    public PrivateDataManager(Connection connection, String user) {
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Must be logged in to XMPP server.");
+        }
+        this.connection = connection;
+        this.user = user;
+    }
+
+    /**
+     * Returns the private data specified by the given element name and namespace. Each chunk
+     * of private data is uniquely identified by an element name and namespace pair.<p>
+     *
+     * If a PrivateDataProvider is registered for the specified element name/namespace pair then
+     * that provider will determine the specific object type that is returned. If no provider
+     * is registered, a {@link DefaultPrivateData} instance will be returned.
+     *
+     * @param elementName the element name.
+     * @param namespace the namespace.
+     * @return the private data.
+     * @throws XMPPException if an error occurs getting the private data.
+     */
+    public PrivateData getPrivateData(final String elementName, final String namespace)
+            throws XMPPException
+    {
+        // Create an IQ packet to get the private data.
+        IQ privateDataGet = new IQ() {
+            public String getChildElementXML() {
+                StringBuilder buf = new StringBuilder();
+                buf.append("<query xmlns=\"jabber:iq:private\">");
+                buf.append("<").append(elementName).append(" xmlns=\"").append(namespace).append("\"/>");
+                buf.append("</query>");
+                return buf.toString();
+            }
+        };
+        privateDataGet.setType(IQ.Type.GET);
+        // Address the packet to the other account if user has been set.
+        if (user != null) {
+            privateDataGet.setTo(user);
+        }
+
+        // Setup a listener for the reply to the set operation.
+        String packetID = privateDataGet.getPacketID();
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(packetID));
+
+        // Send the private data.
+        connection.sendPacket(privateDataGet);
+
+        // Wait up to five seconds for a response from the server.
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+        return ((PrivateDataResult)response).getPrivateData();
+    }
+
+    /**
+     * Sets a private data value. Each chunk of private data is uniquely identified by an
+     * element name and namespace pair. If private data has already been set with the
+     * element name and namespace, then the new private data will overwrite the old value.
+     *
+     * @param privateData the private data.
+     * @throws XMPPException if setting the private data fails.
+     */
+    public void setPrivateData(final PrivateData privateData) throws XMPPException {
+        // Create an IQ packet to set the private data.
+        IQ privateDataSet = new IQ() {
+            public String getChildElementXML() {
+                StringBuilder buf = new StringBuilder();
+                buf.append("<query xmlns=\"jabber:iq:private\">");
+                buf.append(privateData.toXML());
+                buf.append("</query>");
+                return buf.toString();
+            }
+        };
+        privateDataSet.setType(IQ.Type.SET);
+        // Address the packet to the other account if user has been set.
+        if (user != null) {
+            privateDataSet.setTo(user);
+        }
+
+        // Setup a listener for the reply to the set operation.
+        String packetID = privateDataSet.getPacketID();
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(packetID));
+
+        // Send the private data.
+        connection.sendPacket(privateDataSet);
+
+        // Wait up to five seconds for a response from the server.
+        IQ response = (IQ)collector.nextResult(5000);
+        // Stop queuing results
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        // If the server replied with an error, throw an exception.
+        else if (response.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Returns a String key for a given element name and namespace.
+     *
+     * @param elementName the element name.
+     * @param namespace the namespace.
+     * @return a unique key for the element name and namespace pair.
+     */
+    private static String getProviderKey(String elementName, String namespace) {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(elementName).append("/><").append(namespace).append("/>");
+        return buf.toString();
+    }
+
+    /**
+     * An IQ provider to parse IQ results containing private data.
+     */
+    public static class PrivateDataIQProvider implements IQProvider {
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            PrivateData privateData = null;
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    String elementName = parser.getName();
+                    String namespace = parser.getNamespace();
+                    // See if any objects are registered to handle this private data type.
+                    PrivateDataProvider provider = getPrivateDataProvider(elementName, namespace);
+                    // If there is a registered provider, use it.
+                    if (provider != null) {
+                        privateData = provider.parsePrivateData(parser);
+                    }
+                    // Otherwise, use a DefaultPrivateData instance to store the private data.
+                    else {
+                        DefaultPrivateData data = new DefaultPrivateData(elementName, namespace);
+                        boolean finished = false;
+                        while (!finished) {
+                            int event = parser.next();
+                            if (event == XmlPullParser.START_TAG) {
+                                String name = parser.getName();
+                                // If an empty element, set the value with the empty string.
+                                if (parser.isEmptyElementTag()) {
+                                    data.setValue(name,"");
+                                }
+                                // Otherwise, get the the element text.
+                                else {
+                                    event = parser.next();
+                                    if (event == XmlPullParser.TEXT) {
+                                        String value = parser.getText();
+                                        data.setValue(name, value);
+                                    }
+                                }
+                            }
+                            else if (event == XmlPullParser.END_TAG) {
+                                if (parser.getName().equals(elementName)) {
+                                    finished = true;
+                                }
+                            }
+                        }
+                        privateData = data;
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("query")) {
+                        done = true;
+                    }
+                }
+            }
+            return new PrivateDataResult(privateData);
+        }
+    }
+
+    /**
+     * An IQ packet to hold PrivateData GET results.
+     */
+    private static class PrivateDataResult extends IQ {
+
+        private PrivateData privateData;
+
+        PrivateDataResult(PrivateData privateData) {
+            this.privateData = privateData;
+        }
+
+        public PrivateData getPrivateData() {
+            return privateData;
+        }
+
+        public String getChildElementXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<query xmlns=\"jabber:iq:private\">");
+            if (privateData != null) {
+                privateData.toXML();
+            }
+            buf.append("</query>");
+            return buf.toString();
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/RemoteRosterEntry.java b/src/org/jivesoftware/smackx/RemoteRosterEntry.java
new file mode 100644
index 0000000..5df3690
--- /dev/null
+++ b/src/org/jivesoftware/smackx/RemoteRosterEntry.java
@@ -0,0 +1,114 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.util.*;
+
+/**
+ * Represents a roster item, which consists of a JID and , their name and
+ * the groups the roster item belongs to. This roster item does not belong
+ * to the local roster. Therefore, it does not persist in the server.<p>
+ *
+ * The idea of a RemoteRosterEntry is to be used as part of a roster exchange.
+ *
+ * @author Gaston Dombiak
+ */
+public class RemoteRosterEntry {
+
+    private String user;
+    private String name;
+    private final List<String> groupNames = new ArrayList<String>();
+
+    /**
+     * Creates a new remote roster entry.
+     *
+     * @param user the user.
+     * @param name the user's name.
+     * @param groups the list of group names the entry will belong to, or <tt>null</tt> if the
+     *      the roster entry won't belong to a group.
+     */
+    public RemoteRosterEntry(String user, String name, String [] groups) {
+        this.user = user;
+        this.name = name;
+		if (groups != null) {
+            groupNames.addAll(Arrays.asList(groups));
+		}
+    }
+
+    /**
+     * Returns the user.
+     *
+     * @return the user.
+     */
+    public String getUser() {
+        return user;
+    }
+
+    /**
+     * Returns the user's name.
+     *
+     * @return the user's name.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Returns an Iterator for the group names (as Strings) that the roster entry
+     * belongs to.
+     *
+     * @return an Iterator for the group names.
+     */
+    public Iterator<String> getGroupNames() {
+        synchronized (groupNames) {
+            return Collections.unmodifiableList(groupNames).iterator();
+        }
+    }
+
+    /**
+     * Returns a String array for the group names that the roster entry
+     * belongs to.
+     *
+     * @return a String[] for the group names.
+     */
+    public String[] getGroupArrayNames() {
+        synchronized (groupNames) {
+            return Collections.unmodifiableList(groupNames).toArray(new String[groupNames.size()]);
+        }
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<item jid=\"").append(user).append("\"");
+        if (name != null) {
+            buf.append(" name=\"").append(name).append("\"");
+        }
+        buf.append(">");
+        synchronized (groupNames) {
+            for (String groupName : groupNames) {
+                buf.append("<group>").append(groupName).append("</group>");
+            }
+        }
+        buf.append("</item>");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/ReportedData.java b/src/org/jivesoftware/smackx/ReportedData.java
new file mode 100644
index 0000000..0d7b760
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ReportedData.java
@@ -0,0 +1,281 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.DataForm;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents a set of data results returned as part of a search. The report is structured 
+ * in columns and rows.
+ * 
+ * @author Gaston Dombiak
+ */
+public class ReportedData {
+    
+    private List<Column> columns = new ArrayList<Column>();
+    private List<Row> rows = new ArrayList<Row>();
+    private String title = "";
+    
+    /**
+     * Returns a new ReportedData if the packet is used for reporting data and includes an 
+     * extension that matches the elementName and namespace "x","jabber:x:data".
+     * 
+     * @param packet the packet used for reporting data.
+     */
+    public static ReportedData getReportedDataFrom(Packet packet) {
+        // Check if the packet includes the DataForm extension
+        PacketExtension packetExtension = packet.getExtension("x","jabber:x:data");
+        if (packetExtension != null) {
+            // Check if the existing DataForm is a result of a search
+            DataForm dataForm = (DataForm) packetExtension;
+            if (dataForm.getReportedData() != null)
+                return new ReportedData(dataForm);
+        }
+        // Otherwise return null
+        return null;
+    }
+
+
+    /**
+     * Creates a new ReportedData based on the returned dataForm from a search
+     *(namespace "jabber:iq:search").
+     *
+     * @param dataForm the dataForm returned from a search (namespace "jabber:iq:search").
+     */
+    private ReportedData(DataForm dataForm) {
+        // Add the columns to the report based on the reported data fields
+        for (Iterator fields = dataForm.getReportedData().getFields(); fields.hasNext();) {
+            FormField field = (FormField)fields.next();
+            columns.add(new Column(field.getLabel(), field.getVariable(), field.getType()));
+        }
+
+        // Add the rows to the report based on the form's items
+        for (Iterator items = dataForm.getItems(); items.hasNext();) {
+            DataForm.Item item = (DataForm.Item)items.next();
+            List<Field> fieldList = new ArrayList<Field>(columns.size());
+            FormField field;
+            for (Iterator fields = item.getFields(); fields.hasNext();) {
+                field = (FormField) fields.next();
+                // The field is created with all the values of the data form's field
+                List<String> values = new ArrayList<String>();
+                for (Iterator<String> it=field.getValues(); it.hasNext();) {
+                    values.add(it.next());
+                }
+                fieldList.add(new Field(field.getVariable(), values));
+            }
+            rows.add(new Row(fieldList));
+        }
+
+        // Set the report's title
+        this.title = dataForm.getTitle();
+    }
+
+
+    public ReportedData(){
+        // Allow for model creation of ReportedData.
+    }
+
+    /**
+     * Adds a new <code>Row</code>.
+     * @param row the new row to add.
+     */
+    public void addRow(Row row){
+        rows.add(row);
+    }
+
+    /**
+     * Adds a new <code>Column</code>
+     * @param column the column to add.
+     */
+    public void addColumn(Column column){
+        columns.add(column);
+    }
+
+
+    /**
+     * Returns an Iterator for the rows returned from a search.
+     *
+     * @return an Iterator for the rows returned from a search.
+     */
+    public Iterator<Row> getRows() {
+        return Collections.unmodifiableList(new ArrayList<Row>(rows)).iterator();
+    }
+
+    /**
+     * Returns an Iterator for the columns returned from a search.
+     *
+     * @return an Iterator for the columns returned from a search.
+     */
+    public Iterator<Column> getColumns() {
+        return Collections.unmodifiableList(new ArrayList<Column>(columns)).iterator();
+    }
+
+
+    /**
+     * Returns the report's title. It is similar to the title on a web page or an X
+     * window.
+     *
+     * @return title of the report.
+     */
+    public String getTitle() {
+        return title;
+    }
+
+    /**
+     *
+     * Represents the columns definition of the reported data.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Column {
+        private String label;
+        private String variable;
+        private String type;
+
+        /**
+         * Creates a new column with the specified definition.
+         *
+         * @param label the columns's label.
+         * @param variable the variable name of the column.
+         * @param type the format for the returned data.
+         */
+        public Column(String label, String variable, String type) {
+            this.label = label;
+            this.variable = variable;
+            this.type = type;
+        }
+
+        /**
+         * Returns the column's label.
+         *
+         * @return label of the column.
+         */
+        public String getLabel() {
+            return label;
+        }
+
+
+        /**
+         * Returns the column's data format. Valid formats are:
+         *
+         * <ul>
+         *  <li>text-single -> single line or word of text
+         *  <li>text-private -> instead of showing the user what they typed, you show ***** to
+         * protect it
+         *  <li>text-multi -> multiple lines of text entry
+         *  <li>list-single -> given a list of choices, pick one
+         *  <li>list-multi -> given a list of choices, pick one or more
+         *  <li>boolean -> 0 or 1, true or false, yes or no. Default value is 0
+         *  <li>fixed -> fixed for putting in text to show sections, or just advertise your web
+         * site in the middle of the form
+         *  <li>hidden -> is not given to the user at all, but returned with the questionnaire
+         *  <li>jid-single -> Jabber ID - choosing a JID from your roster, and entering one based
+         * on the rules for a JID.
+         *  <li>jid-multi -> multiple entries for JIDs
+         * </ul>
+         *
+         * @return format for the returned data.
+         */
+        public String getType() {
+            return type;
+        }
+
+
+        /**
+         * Returns the variable name that the column is showing.
+         *
+         * @return the variable name of the column.
+         */
+        public String getVariable() {
+            return variable;
+        }
+
+
+    }
+
+    public static class Row {
+        private List<Field> fields = new ArrayList<Field>();
+
+        public Row(List<Field> fields) {
+            this.fields = fields;
+        }
+
+        /**
+         * Returns the values of the field whose variable matches the requested variable.
+         *
+         * @param variable the variable to match.
+         * @return the values of the field whose variable matches the requested variable.
+         */
+        public Iterator getValues(String variable) {
+            for(Iterator<Field> it=getFields();it.hasNext();) {
+                Field field = it.next();
+                if (variable.equalsIgnoreCase(field.getVariable())) {
+                    return field.getValues();
+                }
+            }
+            return null;
+        }
+
+        /**
+         * Returns the fields that define the data that goes with the item.
+         *
+         * @return the fields that define the data that goes with the item.
+         */
+        private Iterator<Field> getFields() {
+            return Collections.unmodifiableList(new ArrayList<Field>(fields)).iterator();
+        }
+    }
+
+    public static class Field {
+        private String variable;
+        private List<String> values;
+
+        public Field(String variable, List<String> values) {
+            this.variable = variable;
+            this.values = values;
+        }
+
+        /**
+         * Returns the variable name that the field represents.
+         * 
+         * @return the variable name of the field.
+         */
+        public String getVariable() {
+            return variable;
+        }
+
+        /**
+         * Returns an iterator on the values reported as part of the search.
+         * 
+         * @return the returned values of the search.
+         */
+        public Iterator<String> getValues() {
+            return Collections.unmodifiableList(values).iterator();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/RosterExchangeListener.java b/src/org/jivesoftware/smackx/RosterExchangeListener.java
new file mode 100644
index 0000000..16ce559
--- /dev/null
+++ b/src/org/jivesoftware/smackx/RosterExchangeListener.java
@@ -0,0 +1,42 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.util.Iterator;
+
+/**
+ *
+ * A listener that is fired anytime a roster exchange is received.
+ *
+ * @author Gaston Dombiak
+ */
+public interface RosterExchangeListener {
+
+    /**
+     * Called when roster entries are received as part of a roster exchange.
+     *  
+     * @param from the user that sent the entries.
+     * @param remoteRosterEntries the entries sent by the user. The entries are instances of 
+     * RemoteRosterEntry.
+     */
+    public void entriesReceived(String from, Iterator<RemoteRosterEntry> remoteRosterEntries);
+
+}
diff --git a/src/org/jivesoftware/smackx/RosterExchangeManager.java b/src/org/jivesoftware/smackx/RosterExchangeManager.java
new file mode 100644
index 0000000..c1d193b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/RosterExchangeManager.java
@@ -0,0 +1,187 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Roster;
+import org.jivesoftware.smack.RosterEntry;
+import org.jivesoftware.smack.RosterGroup;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.packet.RosterExchange;
+
+/**
+ *
+ * Manages Roster exchanges. A RosterExchangeManager provides a high level access to send 
+ * rosters, roster groups and roster entries to XMPP clients. It also provides an easy way
+ * to hook up custom logic when entries are received from another XMPP client through 
+ * RosterExchangeListeners.
+ *
+ * @author Gaston Dombiak
+ */
+public class RosterExchangeManager {
+
+    private List<RosterExchangeListener> rosterExchangeListeners = new ArrayList<RosterExchangeListener>();
+
+    private Connection con;
+
+    private PacketFilter packetFilter = new PacketExtensionFilter("x", "jabber:x:roster");
+    private PacketListener packetListener;
+
+    /**
+     * Creates a new roster exchange manager.
+     *
+     * @param con a Connection which is used to send and receive messages.
+     */
+    public RosterExchangeManager(Connection con) {
+        this.con = con;
+        init();
+    }
+
+    /**
+     * Adds a listener to roster exchanges. The listener will be fired anytime roster entries
+     * are received from remote XMPP clients.
+     *
+     * @param rosterExchangeListener a roster exchange listener.
+     */
+    public void addRosterListener(RosterExchangeListener rosterExchangeListener) {
+        synchronized (rosterExchangeListeners) {
+            if (!rosterExchangeListeners.contains(rosterExchangeListener)) {
+                rosterExchangeListeners.add(rosterExchangeListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener from roster exchanges. The listener will be fired anytime roster 
+     * entries are received from remote XMPP clients.
+     *
+     * @param rosterExchangeListener a roster exchange listener..
+     */
+    public void removeRosterListener(RosterExchangeListener rosterExchangeListener) {
+        synchronized (rosterExchangeListeners) {
+            rosterExchangeListeners.remove(rosterExchangeListener);
+        }
+    }
+
+    /**
+     * Sends a roster to userID. All the entries of the roster will be sent to the
+     * target user.
+     * 
+     * @param roster the roster to send
+     * @param targetUserID the user that will receive the roster entries
+     */
+    public void send(Roster roster, String targetUserID) {
+        // Create a new message to send the roster
+        Message msg = new Message(targetUserID);
+        // Create a RosterExchange Package and add it to the message
+        RosterExchange rosterExchange = new RosterExchange(roster);
+        msg.addExtension(rosterExchange);
+
+        // Send the message that contains the roster
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Sends a roster entry to userID.
+     * 
+     * @param rosterEntry the roster entry to send
+     * @param targetUserID the user that will receive the roster entries
+     */
+    public void send(RosterEntry rosterEntry, String targetUserID) {
+        // Create a new message to send the roster
+        Message msg = new Message(targetUserID);
+        // Create a RosterExchange Package and add it to the message
+        RosterExchange rosterExchange = new RosterExchange();
+        rosterExchange.addRosterEntry(rosterEntry);
+        msg.addExtension(rosterExchange);
+
+        // Send the message that contains the roster
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Sends a roster group to userID. All the entries of the group will be sent to the 
+     * target user.
+     * 
+     * @param rosterGroup the roster group to send
+     * @param targetUserID the user that will receive the roster entries
+     */
+    public void send(RosterGroup rosterGroup, String targetUserID) {
+        // Create a new message to send the roster
+        Message msg = new Message(targetUserID);
+        // Create a RosterExchange Package and add it to the message
+        RosterExchange rosterExchange = new RosterExchange();
+        for (RosterEntry entry : rosterGroup.getEntries()) {
+            rosterExchange.addRosterEntry(entry);
+        }
+        msg.addExtension(rosterExchange);
+
+        // Send the message that contains the roster
+        con.sendPacket(msg);
+    }
+
+    /**
+     * Fires roster exchange listeners.
+     */
+    private void fireRosterExchangeListeners(String from, Iterator<RemoteRosterEntry> remoteRosterEntries) {
+        RosterExchangeListener[] listeners = null;
+        synchronized (rosterExchangeListeners) {
+            listeners = new RosterExchangeListener[rosterExchangeListeners.size()];
+            rosterExchangeListeners.toArray(listeners);
+        }
+        for (int i = 0; i < listeners.length; i++) {
+            listeners[i].entriesReceived(from, remoteRosterEntries);
+        }
+    }
+
+    private void init() {
+        // Listens for all roster exchange packets and fire the roster exchange listeners.
+        packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                Message message = (Message) packet;
+                RosterExchange rosterExchange =
+                    (RosterExchange) message.getExtension("x", "jabber:x:roster");
+                // Fire event for roster exchange listeners
+                fireRosterExchangeListeners(message.getFrom(), rosterExchange.getRosterEntries());
+            };
+
+        };
+        con.addPacketListener(packetListener, packetFilter);
+    }
+
+    public void destroy() {
+        if (con != null)
+            con.removePacketListener(packetListener);
+
+    }
+    protected void finalize() throws Throwable {
+        destroy();
+        super.finalize();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/ServiceDiscoveryManager.java b/src/org/jivesoftware/smackx/ServiceDiscoveryManager.java
new file mode 100644
index 0000000..9e31f67
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ServiceDiscoveryManager.java
@@ -0,0 +1,708 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smackx.entitycaps.EntityCapsManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.DataForm;
+
+import java.util.*;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * Manages discovery of services in XMPP entities. This class provides:
+ * <ol>
+ * <li>A registry of supported features in this XMPP entity.
+ * <li>Automatic response when this XMPP entity is queried for information.
+ * <li>Ability to discover items and information of remote XMPP entities.
+ * <li>Ability to publish publicly available items.
+ * </ol>  
+ * 
+ * @author Gaston Dombiak
+ */
+public class ServiceDiscoveryManager {
+
+    private static final String DEFAULT_IDENTITY_NAME = "Smack";
+    private static final String DEFAULT_IDENTITY_CATEGORY = "client";
+    private static final String DEFAULT_IDENTITY_TYPE = "pc";
+
+    private static List<DiscoverInfo.Identity> identities = new LinkedList<DiscoverInfo.Identity>();
+
+    private EntityCapsManager capsManager;
+
+    private static Map<Connection, ServiceDiscoveryManager> instances =
+            new ConcurrentHashMap<Connection, ServiceDiscoveryManager>();
+
+    private Connection connection;
+    private final Set<String> features = new HashSet<String>();
+    private DataForm extendedInfo = null;
+    private Map<String, NodeInformationProvider> nodeInformationProviders =
+            new ConcurrentHashMap<String, NodeInformationProvider>();
+
+    // Create a new ServiceDiscoveryManager on every established connection
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new ServiceDiscoveryManager(connection);
+            }
+        });
+        identities.add(new Identity(DEFAULT_IDENTITY_CATEGORY, DEFAULT_IDENTITY_NAME, DEFAULT_IDENTITY_TYPE));
+    }
+
+    /**
+     * Creates a new ServiceDiscoveryManager for a given Connection. This means that the 
+     * service manager will respond to any service discovery request that the connection may
+     * receive. 
+     * 
+     * @param connection the connection to which a ServiceDiscoveryManager is going to be created.
+     */
+    public ServiceDiscoveryManager(Connection connection) {
+        this.connection = connection;
+
+        init();
+    }
+
+    /**
+     * Returns the ServiceDiscoveryManager instance associated with a given Connection.
+     * 
+     * @param connection the connection used to look for the proper ServiceDiscoveryManager.
+     * @return the ServiceDiscoveryManager associated with a given Connection.
+     */
+    public static ServiceDiscoveryManager getInstanceFor(Connection connection) {
+        return instances.get(connection);
+    }
+
+    /**
+     * Returns the name of the client that will be returned when asked for the client identity
+     * in a disco request. The name could be any value you need to identity this client.
+     * 
+     * @return the name of the client that will be returned when asked for the client identity
+     *          in a disco request.
+     */
+    public static String getIdentityName() {
+        DiscoverInfo.Identity identity = identities.get(0);
+        if (identity != null) {
+            return identity.getName();
+        } else {
+            return null;
+        }
+    }
+
+    /**
+     * Sets the name of the client that will be returned when asked for the client identity
+     * in a disco request. The name could be any value you need to identity this client.
+     * 
+     * @param name the name of the client that will be returned when asked for the client identity
+     *          in a disco request.
+     */
+    public static void setIdentityName(String name) {
+        DiscoverInfo.Identity identity = identities.remove(0);
+        identity = new DiscoverInfo.Identity(DEFAULT_IDENTITY_CATEGORY, name, DEFAULT_IDENTITY_TYPE);
+        identities.add(identity);
+    }
+
+    /**
+     * Returns the type of client that will be returned when asked for the client identity in a 
+     * disco request. The valid types are defined by the category client. Follow this link to learn 
+     * the possible types: <a href="http://xmpp.org/registrar/disco-categories.html#client">Jabber::Registrar</a>.
+     * 
+     * @return the type of client that will be returned when asked for the client identity in a 
+     *          disco request.
+     */
+    public static String getIdentityType() {
+        DiscoverInfo.Identity identity = identities.get(0);
+        if (identity != null) {
+            return identity.getType();
+        } else {
+            return null;
+        }
+    }
+
+    /**
+     * Sets the type of client that will be returned when asked for the client identity in a 
+     * disco request. The valid types are defined by the category client. Follow this link to learn 
+     * the possible types: <a href="http://xmpp.org/registrar/disco-categories.html#client">Jabber::Registrar</a>.
+     * 
+     * @param type the type of client that will be returned when asked for the client identity in a 
+     *          disco request.
+     */
+    public static void setIdentityType(String type) {
+        DiscoverInfo.Identity identity = identities.get(0);
+        if (identity != null) {
+            identity.setType(type);
+        } else {
+            identity = new DiscoverInfo.Identity(DEFAULT_IDENTITY_CATEGORY, DEFAULT_IDENTITY_NAME, type);
+            identities.add(identity);
+        }
+    }
+
+    /**
+     * Returns all identities of this client as unmodifiable Collection
+     * 
+     * @return
+     */
+    public static List<DiscoverInfo.Identity> getIdentities() {
+        return Collections.unmodifiableList(identities);
+    }
+
+    /**
+     * Initializes the packet listeners of the connection that will answer to any
+     * service discovery request. 
+     */
+    private void init() {
+        // Register the new instance and associate it with the connection 
+        instances.put(connection, this);
+
+        addFeature(DiscoverInfo.NAMESPACE);
+        addFeature(DiscoverItems.NAMESPACE);
+
+        // Add a listener to the connection that removes the registered instance when
+        // the connection is closed
+        connection.addConnectionListener(new ConnectionListener() {
+            public void connectionClosed() {
+                // Unregister this instance since the connection has been closed
+                instances.remove(connection);
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                // ignore
+            }
+
+            public void reconnectionFailed(Exception e) {
+                // ignore
+            }
+
+            public void reconnectingIn(int seconds) {
+                // ignore
+            }
+
+            public void reconnectionSuccessful() {
+                // ignore
+            }
+        });
+
+        // Listen for disco#items requests and answer with an empty result        
+        PacketFilter packetFilter = new PacketTypeFilter(DiscoverItems.class);
+        PacketListener packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                DiscoverItems discoverItems = (DiscoverItems) packet;
+                // Send back the items defined in the client if the request is of type GET
+                if (discoverItems != null && discoverItems.getType() == IQ.Type.GET) {
+                    DiscoverItems response = new DiscoverItems();
+                    response.setType(IQ.Type.RESULT);
+                    response.setTo(discoverItems.getFrom());
+                    response.setPacketID(discoverItems.getPacketID());
+                    response.setNode(discoverItems.getNode());
+
+                    // Add the defined items related to the requested node. Look for 
+                    // the NodeInformationProvider associated with the requested node.  
+                    NodeInformationProvider nodeInformationProvider =
+                            getNodeInformationProvider(discoverItems.getNode());
+                    if (nodeInformationProvider != null) {
+                        // Specified node was found, add node items
+                        response.addItems(nodeInformationProvider.getNodeItems());
+                        // Add packet extensions
+                        response.addExtensions(nodeInformationProvider.getNodePacketExtensions());
+                    } else if(discoverItems.getNode() != null) {
+                        // Return <item-not-found/> error since client doesn't contain
+                        // the specified node
+                        response.setType(IQ.Type.ERROR);
+                        response.setError(new XMPPError(XMPPError.Condition.item_not_found));
+                    }
+                    connection.sendPacket(response);
+                }
+            }
+        };
+        connection.addPacketListener(packetListener, packetFilter);
+
+        // Listen for disco#info requests and answer the client's supported features 
+        // To add a new feature as supported use the #addFeature message        
+        packetFilter = new PacketTypeFilter(DiscoverInfo.class);
+        packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                DiscoverInfo discoverInfo = (DiscoverInfo) packet;
+                // Answer the client's supported features if the request is of the GET type
+                if (discoverInfo != null && discoverInfo.getType() == IQ.Type.GET) {
+                    DiscoverInfo response = new DiscoverInfo();
+                    response.setType(IQ.Type.RESULT);
+                    response.setTo(discoverInfo.getFrom());
+                    response.setPacketID(discoverInfo.getPacketID());
+                    response.setNode(discoverInfo.getNode());
+                    // Add the client's identity and features only if "node" is null
+                    // and if the request was not send to a node. If Entity Caps are
+                    // enabled the client's identity and features are may also added
+                    // if the right node is chosen
+                    if (discoverInfo.getNode() == null) {
+                        addDiscoverInfoTo(response);
+                    }
+                    else {
+                        // Disco#info was sent to a node. Check if we have information of the
+                        // specified node
+                        NodeInformationProvider nodeInformationProvider =
+                                getNodeInformationProvider(discoverInfo.getNode());
+                        if (nodeInformationProvider != null) {
+                            // Node was found. Add node features
+                            response.addFeatures(nodeInformationProvider.getNodeFeatures());
+                            // Add node identities
+                            response.addIdentities(nodeInformationProvider.getNodeIdentities());
+                            // Add packet extensions
+                            response.addExtensions(nodeInformationProvider.getNodePacketExtensions());
+                        }
+                        else {
+                            // Return <item-not-found/> error since specified node was not found
+                            response.setType(IQ.Type.ERROR);
+                            response.setError(new XMPPError(XMPPError.Condition.item_not_found));
+                        }
+                    }
+                    connection.sendPacket(response);
+                }
+            }
+        };
+        connection.addPacketListener(packetListener, packetFilter);
+    }
+
+    /**
+     * Add discover info response data.
+     * 
+     * @see <a href="http://xmpp.org/extensions/xep-0030.html#info-basic">XEP-30 Basic Protocol; Example 2</a>
+     *
+     * @param response the discover info response packet
+     */
+    public void addDiscoverInfoTo(DiscoverInfo response) {
+        // First add the identities of the connection
+        response.addIdentities(identities);
+
+        // Add the registered features to the response
+        synchronized (features) {
+            for (Iterator<String> it = getFeatures(); it.hasNext();) {
+                response.addFeature(it.next());
+            }
+            response.addExtension(extendedInfo);
+        }
+    }
+
+    /**
+     * Returns the NodeInformationProvider responsible for providing information 
+     * (ie items) related to a given node or <tt>null</null> if none.<p>
+     * 
+     * In MUC, a node could be 'http://jabber.org/protocol/muc#rooms' which means that the
+     * NodeInformationProvider will provide information about the rooms where the user has joined.
+     * 
+     * @param node the node that contains items associated with an entity not addressable as a JID.
+     * @return the NodeInformationProvider responsible for providing information related 
+     * to a given node.
+     */
+    private NodeInformationProvider getNodeInformationProvider(String node) {
+        if (node == null) {
+            return null;
+        }
+        return nodeInformationProviders.get(node);
+    }
+
+    /**
+     * Sets the NodeInformationProvider responsible for providing information 
+     * (ie items) related to a given node. Every time this client receives a disco request
+     * regarding the items of a given node, the provider associated to that node will be the 
+     * responsible for providing the requested information.<p>
+     * 
+     * In MUC, a node could be 'http://jabber.org/protocol/muc#rooms' which means that the
+     * NodeInformationProvider will provide information about the rooms where the user has joined. 
+     * 
+     * @param node the node whose items will be provided by the NodeInformationProvider.
+     * @param listener the NodeInformationProvider responsible for providing items related
+     *      to the node.
+     */
+    public void setNodeInformationProvider(String node, NodeInformationProvider listener) {
+        nodeInformationProviders.put(node, listener);
+    }
+
+    /**
+     * Removes the NodeInformationProvider responsible for providing information 
+     * (ie items) related to a given node. This means that no more information will be
+     * available for the specified node.
+     * 
+     * In MUC, a node could be 'http://jabber.org/protocol/muc#rooms' which means that the
+     * NodeInformationProvider will provide information about the rooms where the user has joined. 
+     * 
+     * @param node the node to remove the associated NodeInformationProvider.
+     */
+    public void removeNodeInformationProvider(String node) {
+        nodeInformationProviders.remove(node);
+    }
+
+    /**
+     * Returns the supported features by this XMPP entity.
+     * 
+     * @return an Iterator on the supported features by this XMPP entity.
+     */
+    public Iterator<String> getFeatures() {
+        synchronized (features) {
+            return Collections.unmodifiableList(new ArrayList<String>(features)).iterator();
+        }
+    }
+
+    /**
+     * Returns the supported features by this XMPP entity.
+     * 
+     * @return a copy of the List on the supported features by this XMPP entity.
+     */
+    public List<String> getFeaturesList() {
+        synchronized (features) {
+            return new LinkedList<String>(features);
+        }
+    }
+
+    /**
+     * Registers that a new feature is supported by this XMPP entity. When this client is 
+     * queried for its information the registered features will be answered.<p>
+     *
+     * Since no packet is actually sent to the server it is safe to perform this operation
+     * before logging to the server. In fact, you may want to configure the supported features
+     * before logging to the server so that the information is already available if it is required
+     * upon login.
+     *
+     * @param feature the feature to register as supported.
+     */
+    public void addFeature(String feature) {
+        synchronized (features) {
+            features.add(feature);
+            renewEntityCapsVersion();
+        }
+    }
+
+    /**
+     * Removes the specified feature from the supported features by this XMPP entity.<p>
+     *
+     * Since no packet is actually sent to the server it is safe to perform this operation
+     * before logging to the server.
+     *
+     * @param feature the feature to remove from the supported features.
+     */
+    public void removeFeature(String feature) {
+        synchronized (features) {
+            features.remove(feature);
+            renewEntityCapsVersion();
+        }
+    }
+
+    /**
+     * Returns true if the specified feature is registered in the ServiceDiscoveryManager.
+     *
+     * @param feature the feature to look for.
+     * @return a boolean indicating if the specified featured is registered or not.
+     */
+    public boolean includesFeature(String feature) {
+        synchronized (features) {
+            return features.contains(feature);
+        }
+    }
+
+    /**
+     * Registers extended discovery information of this XMPP entity. When this
+     * client is queried for its information this data form will be returned as
+     * specified by XEP-0128.
+     * <p>
+     *
+     * Since no packet is actually sent to the server it is safe to perform this
+     * operation before logging to the server. In fact, you may want to
+     * configure the extended info before logging to the server so that the
+     * information is already available if it is required upon login.
+     *
+     * @param info
+     *            the data form that contains the extend service discovery
+     *            information.
+     */
+    public void setExtendedInfo(DataForm info) {
+      extendedInfo = info;
+      renewEntityCapsVersion();
+    }
+
+    /**
+     * Returns the data form that is set as extended information for this Service Discovery instance (XEP-0128)
+     * 
+     * @see <a href="http://xmpp.org/extensions/xep-0128.html">XEP-128: Service Discovery Extensions</a>
+     * @return
+     */
+    public DataForm getExtendedInfo() {
+        return extendedInfo;
+    }
+
+    /**
+     * Returns the data form as List of PacketExtensions, or null if no data form is set.
+     * This representation is needed by some classes (e.g. EntityCapsManager, NodeInformationProvider)
+     * 
+     * @return
+     */
+    public List<PacketExtension> getExtendedInfoAsList() {
+        List<PacketExtension> res = null;
+        if (extendedInfo != null) {
+            res = new ArrayList<PacketExtension>(1);
+            res.add(extendedInfo);
+        }
+        return res;
+    }
+
+    /**
+     * Removes the data form containing extended service discovery information
+     * from the information returned by this XMPP entity.<p>
+     *
+     * Since no packet is actually sent to the server it is safe to perform this
+     * operation before logging to the server.
+     */
+    public void removeExtendedInfo() {
+       extendedInfo = null;
+       renewEntityCapsVersion();
+    }
+
+    /**
+     * Returns the discovered information of a given XMPP entity addressed by its JID.
+     * Use null as entityID to query the server
+     * 
+     * @param entityID the address of the XMPP entity or null.
+     * @return the discovered information.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public DiscoverInfo discoverInfo(String entityID) throws XMPPException {
+        if (entityID == null)
+            return discoverInfo(null, null);
+
+        // Check if the have it cached in the Entity Capabilities Manager
+        DiscoverInfo info = EntityCapsManager.getDiscoverInfoByUser(entityID);
+
+        if (info != null) {
+            // We were able to retrieve the information from Entity Caps and
+            // avoided a disco request, hurray!
+            return info;
+        }
+
+        // Try to get the newest node#version if it's known, otherwise null is
+        // returned
+        EntityCapsManager.NodeVerHash nvh = EntityCapsManager.getNodeVerHashByJid(entityID);
+
+        // Discover by requesting the information from the remote entity
+        // Note that wee need to use NodeVer as argument for Node if it exists
+        info = discoverInfo(entityID, nvh != null ? nvh.getNodeVer() : null);
+
+        // If the node version is known, store the new entry.
+        if (nvh != null) {
+            if (EntityCapsManager.verifyDiscoverInfoVersion(nvh.getVer(), nvh.getHash(), info))
+                EntityCapsManager.addDiscoverInfoByNode(nvh.getNodeVer(), info);
+        }
+
+        return info;
+    }
+
+    /**
+     * Returns the discovered information of a given XMPP entity addressed by its JID and
+     * note attribute. Use this message only when trying to query information which is not 
+     * directly addressable.
+     * 
+     * @see <a href="http://xmpp.org/extensions/xep-0030.html#info-basic">XEP-30 Basic Protocol</a>
+     * @see <a href="http://xmpp.org/extensions/xep-0030.html#info-nodes">XEP-30 Info Nodes</a>
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @param node the optional attribute that supplements the 'jid' attribute.
+     * @return the discovered information.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public DiscoverInfo discoverInfo(String entityID, String node) throws XMPPException {
+        // Discover the entity's info
+        DiscoverInfo disco = new DiscoverInfo();
+        disco.setType(IQ.Type.GET);
+        disco.setTo(entityID);
+        disco.setNode(node);
+
+        // Create a packet collector to listen for a response.
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(disco.getPacketID()));
+
+        connection.sendPacket(disco);
+
+        // Wait up to 5 seconds for a result.
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+        return (DiscoverInfo) result;
+    }
+
+    /**
+     * Returns the discovered items of a given XMPP entity addressed by its JID.
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @return the discovered information.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public DiscoverItems discoverItems(String entityID) throws XMPPException {
+        return discoverItems(entityID, null);
+    }
+
+    /**
+     * Returns the discovered items of a given XMPP entity addressed by its JID and
+     * note attribute. Use this message only when trying to query information which is not 
+     * directly addressable.
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @param node the optional attribute that supplements the 'jid' attribute.
+     * @return the discovered items.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public DiscoverItems discoverItems(String entityID, String node) throws XMPPException {
+        // Discover the entity's items
+        DiscoverItems disco = new DiscoverItems();
+        disco.setType(IQ.Type.GET);
+        disco.setTo(entityID);
+        disco.setNode(node);
+
+        // Create a packet collector to listen for a response.
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(disco.getPacketID()));
+
+        connection.sendPacket(disco);
+
+        // Wait up to 5 seconds for a result.
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+        return (DiscoverItems) result;
+    }
+
+    /**
+     * Returns true if the server supports publishing of items. A client may wish to publish items
+     * to the server so that the server can provide items associated to the client. These items will
+     * be returned by the server whenever the server receives a disco request targeted to the bare
+     * address of the client (i.e. user@host.com).
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @return true if the server supports publishing of items.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public boolean canPublishItems(String entityID) throws XMPPException {
+        DiscoverInfo info = discoverInfo(entityID);
+        return canPublishItems(info);
+     }
+
+     /**
+      * Returns true if the server supports publishing of items. A client may wish to publish items
+      * to the server so that the server can provide items associated to the client. These items will
+      * be returned by the server whenever the server receives a disco request targeted to the bare
+      * address of the client (i.e. user@host.com).
+      * 
+      * @param DiscoverInfo the discover info packet to check.
+      * @return true if the server supports publishing of items.
+      */
+     public static boolean canPublishItems(DiscoverInfo info) {
+         return info.containsFeature("http://jabber.org/protocol/disco#publish");
+     }
+
+    /**
+     * Publishes new items to a parent entity. The item elements to publish MUST have at least 
+     * a 'jid' attribute specifying the Entity ID of the item, and an action attribute which 
+     * specifies the action being taken for that item. Possible action values are: "update" and 
+     * "remove".
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @param discoverItems the DiscoveryItems to publish.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public void publishItems(String entityID, DiscoverItems discoverItems)
+            throws XMPPException {
+        publishItems(entityID, null, discoverItems);
+    }
+
+    /**
+     * Publishes new items to a parent entity and node. The item elements to publish MUST have at 
+     * least a 'jid' attribute specifying the Entity ID of the item, and an action attribute which 
+     * specifies the action being taken for that item. Possible action values are: "update" and 
+     * "remove".
+     * 
+     * @param entityID the address of the XMPP entity.
+     * @param node the attribute that supplements the 'jid' attribute.
+     * @param discoverItems the DiscoveryItems to publish.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public void publishItems(String entityID, String node, DiscoverItems discoverItems)
+            throws XMPPException {
+        discoverItems.setType(IQ.Type.SET);
+        discoverItems.setTo(entityID);
+        discoverItems.setNode(node);
+
+        // Create a packet collector to listen for a response.
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(discoverItems.getPacketID()));
+
+        connection.sendPacket(discoverItems);
+
+        // Wait up to 5 seconds for a result.
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+    }
+
+    /**
+     * Entity Capabilities
+     */
+
+    /**
+     * Loads the ServiceDiscoveryManager with an EntityCapsManger
+     * that speeds up certain lookups
+     * @param manager
+     */
+    public void setEntityCapsManager(EntityCapsManager manager) {
+        capsManager = manager;
+    }
+
+    /**
+     * Updates the Entity Capabilities Verification String
+     * if EntityCaps is enabled
+     */
+    private void renewEntityCapsVersion() {
+        if (capsManager != null && capsManager.entityCapsEnabled())
+            capsManager.updateLocalEntityCaps();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/SharedGroupManager.java b/src/org/jivesoftware/smackx/SharedGroupManager.java
new file mode 100644
index 0000000..76cd527
--- /dev/null
+++ b/src/org/jivesoftware/smackx/SharedGroupManager.java
@@ -0,0 +1,72 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.packet.SharedGroupsInfo;
+
+import java.util.List;
+
+/**
+ * A SharedGroupManager provides services for discovering the shared groups where a user belongs.<p>
+ *
+ * Important note: This functionality is not part of the XMPP spec and it will only work
+ * with Wildfire.
+ *
+ * @author Gaston Dombiak
+ */
+public class SharedGroupManager {
+
+    /**
+     * Returns the collection that will contain the name of the shared groups where the user
+     * logged in with the specified session belongs.
+     *
+     * @param connection connection to use to get the user's shared groups.
+     * @return collection with the shared groups' name of the logged user.
+     */
+    public static List<String> getSharedGroups(Connection connection) throws XMPPException {
+        // Discover the shared groups of the logged user
+        SharedGroupsInfo info = new SharedGroupsInfo();
+        info.setType(IQ.Type.GET);
+
+        // Create a packet collector to listen for a response.
+        PacketCollector collector =
+            connection.createPacketCollector(new PacketIDFilter(info.getPacketID()));
+
+        connection.sendPacket(info);
+
+        // Wait up to 5 seconds for a result.
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+        return ((SharedGroupsInfo) result).getGroups();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/XHTMLManager.java b/src/org/jivesoftware/smackx/XHTMLManager.java
new file mode 100644
index 0000000..a446819
--- /dev/null
+++ b/src/org/jivesoftware/smackx/XHTMLManager.java
@@ -0,0 +1,144 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.XHTMLExtension;
+
+import java.util.Iterator;
+
+/**
+ * Manages XHTML formatted texts within messages. A XHTMLManager provides a high level access to 
+ * get and set XHTML bodies to messages, enable and disable XHTML support and check if remote XMPP
+ * clients support XHTML.   
+ * 
+ * @author Gaston Dombiak
+ */
+public class XHTMLManager {
+
+    private final static String namespace = "http://jabber.org/protocol/xhtml-im";
+
+    // Enable the XHTML support on every established connection
+    // The ServiceDiscoveryManager class should have been already initialized
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                XHTMLManager.setServiceEnabled(connection, true);
+            }
+        });
+    }
+
+    /**
+     * Returns an Iterator for the XHTML bodies in the message. Returns null if 
+     * the message does not contain an XHTML extension.
+     *
+     * @param message an XHTML message
+     * @return an Iterator for the bodies in the message or null if none.
+     */
+    public static Iterator<String> getBodies(Message message) {
+        XHTMLExtension xhtmlExtension = (XHTMLExtension) message.getExtension("html", namespace);
+        if (xhtmlExtension != null)
+            return xhtmlExtension.getBodies();
+        else
+            return null;
+    }
+
+    /**
+     * Adds an XHTML body to the message.
+     *
+     * @param message the message that will receive the XHTML body
+     * @param body the string to add as an XHTML body to the message
+     */
+    public static void addBody(Message message, String body) {
+        XHTMLExtension xhtmlExtension = (XHTMLExtension) message.getExtension("html", namespace);
+        if (xhtmlExtension == null) {
+            // Create an XHTMLExtension and add it to the message
+            xhtmlExtension = new XHTMLExtension();
+            message.addExtension(xhtmlExtension);
+        }
+        // Add the required bodies to the message
+        xhtmlExtension.addBody(body);
+    }
+
+    /**
+     * Returns true if the message contains an XHTML extension.
+     *
+     * @param message the message to check if contains an XHTML extentsion or not
+     * @return a boolean indicating whether the message is an XHTML message
+     */
+    public static boolean isXHTMLMessage(Message message) {
+        return message.getExtension("html", namespace) != null;
+    }
+
+    /**
+     * Enables or disables the XHTML support on a given connection.<p>
+     *  
+     * Before starting to send XHTML messages to a user, check that the user can handle XHTML
+     * messages. Enable the XHTML support to indicate that this client handles XHTML messages.  
+     *
+     * @param connection the connection where the service will be enabled or disabled
+     * @param enabled indicates if the service will be enabled or disabled 
+     */
+    public synchronized static void setServiceEnabled(Connection connection, boolean enabled) {
+        if (isServiceEnabled(connection) == enabled)
+            return;
+
+        if (enabled) {
+            ServiceDiscoveryManager.getInstanceFor(connection).addFeature(namespace);
+        }
+        else {
+            ServiceDiscoveryManager.getInstanceFor(connection).removeFeature(namespace);
+        }
+    }
+
+    /**
+     * Returns true if the XHTML support is enabled for the given connection.
+     *
+     * @param connection the connection to look for XHTML support
+     * @return a boolean indicating if the XHTML support is enabled for the given connection
+     */
+    public static boolean isServiceEnabled(Connection connection) {
+        return ServiceDiscoveryManager.getInstanceFor(connection).includesFeature(namespace);
+    }
+
+    /**
+     * Returns true if the specified user handles XHTML messages.
+     *
+     * @param connection the connection to use to perform the service discovery
+     * @param userID the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com
+     * @return a boolean indicating whether the specified user handles XHTML messages
+     */
+    public static boolean isServiceEnabled(Connection connection, String userID) {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(userID);
+            return result.containsFeature(namespace);
+        }
+        catch (XMPPException e) {
+            e.printStackTrace();
+            return false;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/XHTMLText.java b/src/org/jivesoftware/smackx/XHTMLText.java
new file mode 100644
index 0000000..201e530
--- /dev/null
+++ b/src/org/jivesoftware/smackx/XHTMLText.java
@@ -0,0 +1,429 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * An XHTMLText represents formatted text. This class also helps to build valid 
+ * XHTML tags.
+ *
+ * @author Gaston Dombiak
+ */
+public class XHTMLText {
+
+    private StringBuilder text = new StringBuilder(30);
+
+    /**
+     * Creates a new XHTMLText with body tag params.
+     * 
+     * @param style the XHTML style of the body
+     * @param lang the language of the body
+     */
+    public XHTMLText(String style, String lang) {
+        appendOpenBodyTag(style, lang);
+    }
+
+    /**
+     * Appends a tag that indicates that an anchor section begins.
+     * 
+     * @param href indicates the URL being linked to
+     * @param style the XHTML style of the anchor
+     */
+    public void appendOpenAnchorTag(String href, String style) {
+        StringBuilder sb = new StringBuilder("<a");
+        if (href != null) {
+            sb.append(" href=\"");
+            sb.append(href);
+            sb.append("\"");
+        }
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that an anchor section ends.
+     * 
+     */
+    public void appendCloseAnchorTag() {
+        text.append("</a>");
+    }
+
+    /**
+     * Appends a tag that indicates that a blockquote section begins.
+     * 
+     * @param style the XHTML style of the blockquote
+     */
+    public void appendOpenBlockQuoteTag(String style) {
+        StringBuilder sb = new StringBuilder("<blockquote");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that a blockquote section ends.
+     * 
+     */
+    public void appendCloseBlockQuoteTag() {
+        text.append("</blockquote>");
+    }
+
+    /**
+     * Appends a tag that indicates that a body section begins.
+     * 
+     * @param style the XHTML style of the body
+     * @param lang the language of the body
+     */
+    private void appendOpenBodyTag(String style, String lang) {
+        StringBuilder sb = new StringBuilder("<body");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        if (lang != null) {
+            sb.append(" xml:lang=\"");
+            sb.append(lang);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that a body section ends.
+     * 
+     */
+    private String closeBodyTag() {
+        return "</body>";
+    }
+
+    /**
+     * Appends a tag that inserts a single carriage return.
+     * 
+     */
+    public void appendBrTag() {
+        text.append("<br/>");
+    }
+
+    /**
+     * Appends a tag that indicates a reference to work, such as a book, report or web site.
+     * 
+     */
+    public void appendOpenCiteTag() {
+        text.append("<cite>");
+    }
+
+    /**
+     * Appends a tag that indicates text that is the code for a program.
+     * 
+     */
+    public void appendOpenCodeTag() {
+        text.append("<code>");
+    }
+
+    /**
+     * Appends a tag that indicates end of text that is the code for a program.
+     * 
+     */
+    public void appendCloseCodeTag() {
+        text.append("</code>");
+    }
+
+    /**
+     * Appends a tag that indicates emphasis.
+     * 
+     */
+    public void appendOpenEmTag() {
+        text.append("<em>");
+    }
+
+    /**
+     * Appends a tag that indicates end of emphasis.
+     * 
+     */
+    public void appendCloseEmTag() {
+        text.append("</em>");
+    }
+
+    /**
+     * Appends a tag that indicates a header, a title of a section of the message.
+     * 
+     * @param level the level of the Header. It should be a value between 1 and 3
+     * @param style the XHTML style of the blockquote
+     */
+    public void appendOpenHeaderTag(int level, String style) {
+        if (level > 3 || level < 1) {
+            return;
+        }
+        StringBuilder sb = new StringBuilder("<h");
+        sb.append(level);
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that a header section ends.
+     * 
+     * @param level the level of the Header. It should be a value between 1 and 3
+     */
+    public void appendCloseHeaderTag(int level) {
+        if (level > 3 || level < 1) {
+            return;
+        }
+        StringBuilder sb = new StringBuilder("</h");
+        sb.append(level);
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates an image.
+     * 
+     * @param align how text should flow around the picture
+     * @param alt the text to show if you don't show the picture
+     * @param height how tall is the picture
+     * @param src where to get the picture
+     * @param width how wide is the picture
+     */
+    public void appendImageTag(String align, String alt, String height, String src, String width) {
+        StringBuilder sb = new StringBuilder("<img");
+        if (align != null) {
+            sb.append(" align=\"");
+            sb.append(align);
+            sb.append("\"");
+        }
+        if (alt != null) {
+            sb.append(" alt=\"");
+            sb.append(alt);
+            sb.append("\"");
+        }
+        if (height != null) {
+            sb.append(" height=\"");
+            sb.append(height);
+            sb.append("\"");
+        }
+        if (src != null) {
+            sb.append(" src=\"");
+            sb.append(src);
+            sb.append("\"");
+        }
+        if (width != null) {
+            sb.append(" width=\"");
+            sb.append(width);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates the start of a new line item within a list.
+     * 
+     * @param style the style of the line item
+     */
+    public void appendLineItemTag(String style) {
+        StringBuilder sb = new StringBuilder("<li");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that creates an ordered list. "Ordered" means that the order of the items 
+     * in the list is important. To show this, browsers automatically number the list. 
+     * 
+     * @param style the style of the ordered list
+     */
+    public void appendOpenOrderedListTag(String style) {
+        StringBuilder sb = new StringBuilder("<ol");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that an ordered list section ends.
+     * 
+     */
+    public void appendCloseOrderedListTag() {
+        text.append("</ol>");
+    }
+
+    /**
+     * Appends a tag that creates an unordered list. The unordered part means that the items 
+     * in the list are not in any particular order.
+     * 
+     * @param style the style of the unordered list
+     */
+    public void appendOpenUnorderedListTag(String style) {
+        StringBuilder sb = new StringBuilder("<ul");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that an unordered list section ends.
+     * 
+     */
+    public void appendCloseUnorderedListTag() {
+        text.append("</ul>");
+    }
+
+    /**
+     * Appends a tag that indicates the start of a new paragraph. This is usually rendered 
+     * with two carriage returns, producing a single blank line in between the two paragraphs.
+     * 
+     * @param style the style of the paragraph
+     */
+    public void appendOpenParagraphTag(String style) {
+        StringBuilder sb = new StringBuilder("<p");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates the end of a new paragraph. This is usually rendered 
+     * with two carriage returns, producing a single blank line in between the two paragraphs.
+     * 
+     */
+    public void appendCloseParagraphTag() {
+        text.append("</p>");
+    }
+
+    /**
+     * Appends a tag that indicates that an inlined quote section begins.
+     * 
+     * @param style the style of the inlined quote
+     */
+    public void appendOpenInlinedQuoteTag(String style) {
+        StringBuilder sb = new StringBuilder("<q");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that an inlined quote section ends.
+     * 
+     */
+    public void appendCloseInlinedQuoteTag() {
+        text.append("</q>");
+    }
+
+    /**
+     * Appends a tag that allows to set the fonts for a span of text.
+     * 
+     * @param style the style for a span of text
+     */
+    public void appendOpenSpanTag(String style) {
+        StringBuilder sb = new StringBuilder("<span");
+        if (style != null) {
+            sb.append(" style=\"");
+            sb.append(style);
+            sb.append("\"");
+        }
+        sb.append(">");
+        text.append(sb.toString());
+    }
+
+    /**
+     * Appends a tag that indicates that a span section ends.
+     * 
+     */
+    public void appendCloseSpanTag() {
+        text.append("</span>");
+    }
+
+    /**
+     * Appends a tag that indicates text which should be more forceful than surrounding text.
+     * 
+     */
+    public void appendOpenStrongTag() {
+        text.append("<strong>");
+    }
+
+    /**
+     * Appends a tag that indicates that a strong section ends.
+     * 
+     */
+    public void appendCloseStrongTag() {
+        text.append("</strong>");
+    }
+
+    /**
+     * Appends a given text to the XHTMLText.
+     * 
+     * @param textToAppend the text to append   
+     */
+    public void append(String textToAppend) {
+        text.append(StringUtils.escapeForXML(textToAppend));
+    }
+
+    /**
+     * Returns the text of the XHTMLText.
+     * 
+     * Note: Automatically adds the closing body tag.
+     * 
+     * @return the text of the XHTMLText   
+     */
+    public String toString() {
+        return text.toString().concat(closeBodyTag());
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bookmark/BookmarkManager.java b/src/org/jivesoftware/smackx/bookmark/BookmarkManager.java
new file mode 100644
index 0000000..f85cc9c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bookmark/BookmarkManager.java
@@ -0,0 +1,224 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.bookmark;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smackx.PrivateDataManager;
+
+import java.util.*;
+
+/**
+ * Provides methods to manage bookmarks in accordance with JEP-0048. Methods for managing URLs and
+ * Conferences are provided.
+ * </p>
+ * It should be noted that some extensions have been made to the JEP. There is an attribute on URLs
+ * that marks a url as a news feed and also a sub-element can be added to either a URL or conference
+ * indicated that it is shared amongst all users on a server.
+ *
+ * @author Alexander Wenckus
+ */
+public class BookmarkManager {
+    private static final Map<Connection, BookmarkManager> bookmarkManagerMap = new HashMap<Connection, BookmarkManager>();
+    static {
+        PrivateDataManager.addPrivateDataProvider("storage", "storage:bookmarks",
+                new Bookmarks.Provider());
+    }
+
+    /**
+     * Returns the <i>BookmarkManager</i> for a connection, if it doesn't exist it is created.
+     *
+     * @param connection the connection for which the manager is desired.
+     * @return Returns the <i>BookmarkManager</i> for a connection, if it doesn't
+     * exist it is created.
+     * @throws XMPPException Thrown if the connection is null or has not yet been authenticated.
+     */
+    public synchronized static BookmarkManager getBookmarkManager(Connection connection)
+            throws XMPPException
+    {
+        BookmarkManager manager = (BookmarkManager) bookmarkManagerMap.get(connection);
+        if(manager == null) {
+            manager = new BookmarkManager(connection);
+            bookmarkManagerMap.put(connection, manager);
+        }
+        return manager;
+    }
+
+    private PrivateDataManager privateDataManager;
+    private Bookmarks bookmarks;
+    private final Object bookmarkLock = new Object();
+
+    /**
+     * Default constructor. Registers the data provider with the private data manager in the
+     * storage:bookmarks namespace.
+     *
+     * @param connection the connection for persisting and retrieving bookmarks.
+     * @throws XMPPException thrown when the connection is null or has not been authenticated.
+     */
+    private BookmarkManager(Connection connection) throws XMPPException {
+        if(connection == null || !connection.isAuthenticated()) {
+            throw new XMPPException("Invalid connection.");
+        }
+        this.privateDataManager = new PrivateDataManager(connection);
+    }
+
+    /**
+     * Returns all currently bookmarked conferences.
+     *
+     * @return returns all currently bookmarked conferences
+     * @throws XMPPException thrown when there was an error retrieving the current bookmarks from
+     * the server.
+     * @see BookmarkedConference
+     */
+    public Collection<BookmarkedConference> getBookmarkedConferences() throws XMPPException {
+        retrieveBookmarks();
+        return Collections.unmodifiableCollection(bookmarks.getBookmarkedConferences());
+    }
+
+    /**
+     * Adds or updates a conference in the bookmarks.
+     *
+     * @param name the name of the conference
+     * @param jid the jid of the conference
+     * @param isAutoJoin whether or not to join this conference automatically on login
+     * @param nickname the nickname to use for the user when joining the conference
+     * @param password the password to use for the user when joining the conference
+     * @throws XMPPException thrown when there is an issue retrieving the current bookmarks from
+     * the server.
+     */
+    public void addBookmarkedConference(String name, String jid, boolean isAutoJoin,
+            String nickname, String password) throws XMPPException
+    {
+        retrieveBookmarks();
+        BookmarkedConference bookmark
+                = new BookmarkedConference(name, jid, isAutoJoin, nickname, password);
+        List<BookmarkedConference> conferences = bookmarks.getBookmarkedConferences();
+        if(conferences.contains(bookmark)) {
+            BookmarkedConference oldConference = conferences.get(conferences.indexOf(bookmark));
+            if(oldConference.isShared()) {
+                throw new IllegalArgumentException("Cannot modify shared bookmark");
+            }
+            oldConference.setAutoJoin(isAutoJoin);
+            oldConference.setName(name);
+            oldConference.setNickname(nickname);
+            oldConference.setPassword(password);
+        }
+        else {
+            bookmarks.addBookmarkedConference(bookmark);
+        }
+        privateDataManager.setPrivateData(bookmarks);
+    }
+
+    /**
+     * Removes a conference from the bookmarks.
+     *
+     * @param jid the jid of the conference to be removed.
+     * @throws XMPPException thrown when there is a problem with the connection attempting to
+     * retrieve the bookmarks or persist the bookmarks.
+     * @throws IllegalArgumentException thrown when the conference being removed is a shared
+     * conference
+     */
+    public void removeBookmarkedConference(String jid) throws XMPPException {
+        retrieveBookmarks();
+        Iterator<BookmarkedConference> it = bookmarks.getBookmarkedConferences().iterator();
+        while(it.hasNext()) {
+            BookmarkedConference conference = it.next();
+            if(conference.getJid().equalsIgnoreCase(jid)) {
+                if(conference.isShared()) {
+                    throw new IllegalArgumentException("Conference is shared and can't be removed");
+                }
+                it.remove();
+                privateDataManager.setPrivateData(bookmarks);
+                return;
+            }
+        }
+    }
+
+    /**
+     * Returns an unmodifiable collection of all bookmarked urls.
+     *
+     * @return returns an unmodifiable collection of all bookmarked urls.
+     * @throws XMPPException thrown when there is a problem retriving bookmarks from the server.
+     */
+    public Collection<BookmarkedURL> getBookmarkedURLs() throws XMPPException {
+        retrieveBookmarks();
+        return Collections.unmodifiableCollection(bookmarks.getBookmarkedURLS());
+    }
+
+    /**
+     * Adds a new url or updates an already existing url in the bookmarks.
+     *
+     * @param URL the url of the bookmark
+     * @param name the name of the bookmark
+     * @param isRSS whether or not the url is an rss feed
+     * @throws XMPPException thrown when there is an error retriving or saving bookmarks from or to
+     * the server
+     */
+    public void addBookmarkedURL(String URL, String name, boolean isRSS) throws XMPPException {
+        retrieveBookmarks();
+        BookmarkedURL bookmark = new BookmarkedURL(URL, name, isRSS);
+        List<BookmarkedURL> urls = bookmarks.getBookmarkedURLS();
+        if(urls.contains(bookmark)) {
+            BookmarkedURL oldURL = urls.get(urls.indexOf(bookmark));
+            if(oldURL.isShared()) {
+                throw new IllegalArgumentException("Cannot modify shared bookmarks");
+            }
+            oldURL.setName(name);
+            oldURL.setRss(isRSS);
+        }
+        else {
+            bookmarks.addBookmarkedURL(bookmark);
+        }
+        privateDataManager.setPrivateData(bookmarks);
+    }
+
+    /**
+     *  Removes a url from the bookmarks.
+     *
+     * @param bookmarkURL the url of the bookmark to remove
+     * @throws XMPPException thrown if there is an error retriving or saving bookmarks from or to
+     * the server.
+     */
+    public void removeBookmarkedURL(String bookmarkURL) throws XMPPException {
+        retrieveBookmarks();
+        Iterator<BookmarkedURL> it = bookmarks.getBookmarkedURLS().iterator();
+        while(it.hasNext()) {
+            BookmarkedURL bookmark = it.next();
+            if(bookmark.getURL().equalsIgnoreCase(bookmarkURL)) {
+                if(bookmark.isShared()) {
+                    throw new IllegalArgumentException("Cannot delete a shared bookmark.");
+                }
+                it.remove();
+                privateDataManager.setPrivateData(bookmarks);
+                return;
+            }
+        }
+    }
+
+    private Bookmarks retrieveBookmarks() throws XMPPException {
+        synchronized(bookmarkLock) {
+            if(bookmarks == null) {
+                bookmarks = (Bookmarks) privateDataManager.getPrivateData("storage",
+                        "storage:bookmarks");
+            }
+            return bookmarks;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/bookmark/BookmarkedConference.java b/src/org/jivesoftware/smackx/bookmark/BookmarkedConference.java
new file mode 100644
index 0000000..5dac202
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bookmark/BookmarkedConference.java
@@ -0,0 +1,130 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.bookmark;
+
+/**
+ * Respresents a Conference Room bookmarked on the server using JEP-0048 Bookmark Storage JEP.
+ *
+ * @author Derek DeMoro
+ */
+public class BookmarkedConference implements SharedBookmark {
+
+    private String name;
+    private boolean autoJoin;
+    private final String jid;
+
+    private String nickname;
+    private String password;
+    private boolean isShared;
+
+    protected BookmarkedConference(String jid) {
+        this.jid = jid;
+    }
+
+    protected BookmarkedConference(String name, String jid, boolean autoJoin, String nickname,
+            String password)
+    {
+        this.name = name;
+        this.jid = jid;
+        this.autoJoin = autoJoin;
+        this.nickname = nickname;
+        this.password = password;
+    }
+
+
+    /**
+     * Returns the display label representing the Conference room.
+     *
+     * @return the name of the conference room.
+     */
+    public String getName() {
+        return name;
+    }
+
+    protected void setName(String name) {
+        this.name = name;
+    }
+
+    /**
+     * Returns true if this conference room should be auto-joined on startup.
+     *
+     * @return true if room should be joined on startup, otherwise false.
+     */
+    public boolean isAutoJoin() {
+        return autoJoin;
+    }
+
+    protected void setAutoJoin(boolean autoJoin) {
+        this.autoJoin = autoJoin;
+    }
+
+    /**
+     * Returns the full JID of this conference room. (ex.dev@conference.jivesoftware.com)
+     *
+     * @return the full JID of  this conference room.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Returns the nickname to use when joining this conference room. This is an optional
+     * value and may return null.
+     *
+     * @return the nickname to use when joining, null may be returned.
+     */
+    public String getNickname() {
+        return nickname;
+    }
+
+    protected void setNickname(String nickname) {
+        this.nickname = nickname;
+    }
+
+    /**
+     * Returns the password to use when joining this conference room. This is an optional
+     * value and may return null.
+     *
+     * @return the password to use when joining this conference room, null may be returned.
+     */
+    public String getPassword() {
+        return password;
+    }
+
+    protected void setPassword(String password) {
+        this.password = password;
+    }
+
+    public boolean equals(Object obj) {
+        if(obj == null || !(obj instanceof BookmarkedConference)) {
+            return false;
+        }
+        BookmarkedConference conference = (BookmarkedConference)obj;
+        return conference.getJid().equalsIgnoreCase(jid);
+    }
+
+    protected void setShared(boolean isShared) {
+        this.isShared = isShared;
+    }
+
+    public boolean isShared() {
+        return isShared;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/bookmark/BookmarkedURL.java b/src/org/jivesoftware/smackx/bookmark/BookmarkedURL.java
new file mode 100644
index 0000000..f3d6d9d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bookmark/BookmarkedURL.java
@@ -0,0 +1,104 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.bookmark;
+
+/**
+ * Respresents one instance of a URL defined using JEP-0048 Bookmark Storage JEP.
+ *
+ * @author Derek DeMoro
+ */
+public class BookmarkedURL implements SharedBookmark {
+
+    private String name;
+    private final String URL;
+    private boolean isRss;
+    private boolean isShared;
+
+    protected BookmarkedURL(String URL) {
+        this.URL = URL;
+    }
+
+    protected BookmarkedURL(String URL, String name, boolean isRss) {
+        this.URL = URL;
+        this.name = name;
+        this.isRss = isRss;
+    }
+
+    /**
+     * Returns the name representing the URL (eg. Jive Software). This can be used in as a label, or
+     * identifer in applications.
+     *
+     * @return the name reprenting the URL.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Sets the name representing the URL.
+     *
+     * @param name the name.
+     */
+    protected void setName(String name) {
+        this.name = name;
+    }
+
+    /**
+     * Returns the URL.
+     *
+     * @return the url.
+     */
+    public String getURL() {
+        return URL;
+    }
+    /**
+     * Set to true if this URL is an RSS or news feed.
+     *
+     * @param isRss True if the URL is a news feed and false if it is not.
+     */
+    protected void setRss(boolean isRss) {
+        this.isRss = isRss;
+    }
+
+    /**
+     * Returns true if this URL is a news feed.
+     *
+     * @return Returns true if this URL is a news feed.
+     */
+    public boolean isRss() {
+        return isRss;
+    }
+
+    public boolean equals(Object obj) {
+        if(!(obj instanceof BookmarkedURL)) {
+            return false;
+        }
+        BookmarkedURL url = (BookmarkedURL)obj;
+        return url.getURL().equalsIgnoreCase(URL);
+    }
+
+    protected void setShared(boolean shared) {
+        this.isShared = shared;
+    }
+
+    public boolean isShared() {
+        return isShared;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/bookmark/Bookmarks.java b/src/org/jivesoftware/smackx/bookmark/Bookmarks.java
new file mode 100644
index 0000000..100fa46
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bookmark/Bookmarks.java
@@ -0,0 +1,310 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bookmark;
+
+import org.jivesoftware.smackx.packet.PrivateData;
+import org.jivesoftware.smackx.provider.PrivateDataProvider;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Bookmarks is used for storing and retrieving URLS and Conference rooms.
+ * Bookmark Storage (JEP-0048) defined a protocol for the storage of bookmarks to conference rooms and other entities
+ * in a Jabber user's account.
+ * See the following code sample for saving Bookmarks:
+ * <p/>
+ * <pre>
+ * Connection con = new XMPPConnection("jabber.org");
+ * con.login("john", "doe");
+ * Bookmarks bookmarks = new Bookmarks();
+ * <p/>
+ * // Bookmark a URL
+ * BookmarkedURL url = new BookmarkedURL();
+ * url.setName("Google");
+ * url.setURL("http://www.jivesoftware.com");
+ * bookmarks.addURL(url);
+ * // Bookmark a Conference room.
+ * BookmarkedConference conference = new BookmarkedConference();
+ * conference.setName("My Favorite Room");
+ * conference.setAutoJoin("true");
+ * conference.setJID("dev@conference.jivesoftware.com");
+ * bookmarks.addConference(conference);
+ * // Save Bookmarks using PrivateDataManager.
+ * PrivateDataManager manager = new PrivateDataManager(con);
+ * manager.setPrivateData(bookmarks);
+ * <p/>
+ * <p/>
+ * LastActivity activity = LastActivity.getLastActivity(con, "xray@jabber.org");
+ * </pre>
+ *
+ * @author Derek DeMoro
+ */
+public class Bookmarks implements PrivateData {
+
+    private List<BookmarkedURL> bookmarkedURLS;
+    private List<BookmarkedConference> bookmarkedConferences;
+
+    /**
+     * Required Empty Constructor to use Bookmarks.
+     */
+    public Bookmarks() {
+        bookmarkedURLS = new ArrayList<BookmarkedURL>();
+        bookmarkedConferences = new ArrayList<BookmarkedConference>();
+    }
+
+    /**
+     * Adds a BookmarkedURL.
+     *
+     * @param bookmarkedURL the bookmarked bookmarkedURL.
+     */
+    public void addBookmarkedURL(BookmarkedURL bookmarkedURL) {
+        bookmarkedURLS.add(bookmarkedURL);
+    }
+
+    /**
+     * Removes a bookmarked bookmarkedURL.
+     *
+     * @param bookmarkedURL the bookmarked bookmarkedURL to remove.
+     */
+    public void removeBookmarkedURL(BookmarkedURL bookmarkedURL) {
+        bookmarkedURLS.remove(bookmarkedURL);
+    }
+
+    /**
+     * Removes all BookmarkedURLs from user's bookmarks.
+     */
+    public void clearBookmarkedURLS() {
+        bookmarkedURLS.clear();
+    }
+
+    /**
+     * Add a BookmarkedConference to bookmarks.
+     *
+     * @param bookmarkedConference the conference to remove.
+     */
+    public void addBookmarkedConference(BookmarkedConference bookmarkedConference) {
+        bookmarkedConferences.add(bookmarkedConference);
+    }
+
+    /**
+     * Removes a BookmarkedConference.
+     *
+     * @param bookmarkedConference the BookmarkedConference to remove.
+     */
+    public void removeBookmarkedConference(BookmarkedConference bookmarkedConference) {
+        bookmarkedConferences.remove(bookmarkedConference);
+    }
+
+    /**
+     * Removes all BookmarkedConferences from Bookmarks.
+     */
+    public void clearBookmarkedConferences() {
+        bookmarkedConferences.clear();
+    }
+
+    /**
+     * Returns a Collection of all Bookmarked URLs for this user.
+     *
+     * @return a collection of all Bookmarked URLs.
+     */
+    public List<BookmarkedURL> getBookmarkedURLS() {
+        return bookmarkedURLS;
+    }
+
+    /**
+     * Returns a Collection of all Bookmarked Conference for this user.
+     *
+     * @return a collection of all Bookmarked Conferences.
+     */
+    public List<BookmarkedConference> getBookmarkedConferences() {
+        return bookmarkedConferences;
+    }
+
+
+    /**
+     * Returns the root element name.
+     *
+     * @return the element name.
+     */
+    public String getElementName() {
+        return "storage";
+    }
+
+    /**
+     * Returns the root element XML namespace.
+     *
+     * @return the namespace.
+     */
+    public String getNamespace() {
+        return "storage:bookmarks";
+    }
+
+    /**
+     * Returns the XML reppresentation of the PrivateData.
+     *
+     * @return the private data as XML.
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<storage xmlns=\"storage:bookmarks\">");
+
+        final Iterator<BookmarkedURL> urls = getBookmarkedURLS().iterator();
+        while (urls.hasNext()) {
+            BookmarkedURL urlStorage = urls.next();
+            if(urlStorage.isShared()) {
+                continue;
+            }
+            buf.append("<url name=\"").append(urlStorage.getName()).
+                    append("\" url=\"").append(urlStorage.getURL()).append("\"");
+            if(urlStorage.isRss()) {
+                buf.append(" rss=\"").append(true).append("\"");
+            }
+            buf.append(" />");
+        }
+
+        // Add Conference additions
+        final Iterator<BookmarkedConference> conferences = getBookmarkedConferences().iterator();
+        while (conferences.hasNext()) {
+            BookmarkedConference conference = conferences.next();
+            if(conference.isShared()) {
+                continue;
+            }
+            buf.append("<conference ");
+            buf.append("name=\"").append(conference.getName()).append("\" ");
+            buf.append("autojoin=\"").append(conference.isAutoJoin()).append("\" ");
+            buf.append("jid=\"").append(conference.getJid()).append("\" ");
+            buf.append(">");
+
+            if (conference.getNickname() != null) {
+                buf.append("<nick>").append(conference.getNickname()).append("</nick>");
+            }
+
+
+            if (conference.getPassword() != null) {
+                buf.append("<password>").append(conference.getPassword()).append("</password>");
+            }
+            buf.append("</conference>");
+        }
+
+
+        buf.append("</storage>");
+        return buf.toString();
+    }
+
+    /**
+     * The IQ Provider for BookmarkStorage.
+     *
+     * @author Derek DeMoro
+     */
+    public static class Provider implements PrivateDataProvider {
+
+        /**
+         * Empty Constructor for PrivateDataProvider.
+         */
+        public Provider() {
+            super();
+        }
+
+        public PrivateData parsePrivateData(XmlPullParser parser) throws Exception {
+            Bookmarks storage = new Bookmarks();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG && "url".equals(parser.getName())) {
+                    final BookmarkedURL urlStorage = getURLStorage(parser);
+                    if (urlStorage != null) {
+                        storage.addBookmarkedURL(urlStorage);
+                    }
+                }
+                else if (eventType == XmlPullParser.START_TAG &&
+                        "conference".equals(parser.getName()))
+                {
+                    final BookmarkedConference conference = getConferenceStorage(parser);
+                    storage.addBookmarkedConference(conference);
+                }
+                else if (eventType == XmlPullParser.END_TAG && "storage".equals(parser.getName()))
+                {
+                    done = true;
+                }
+            }
+
+
+            return storage;
+        }
+    }
+
+    private static BookmarkedURL getURLStorage(XmlPullParser parser) throws IOException, XmlPullParserException {
+        String name = parser.getAttributeValue("", "name");
+        String url = parser.getAttributeValue("", "url");
+        String rssString = parser.getAttributeValue("", "rss");
+        boolean rss = rssString != null && "true".equals(rssString);
+
+        BookmarkedURL urlStore = new BookmarkedURL(url, name, rss);
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if(eventType == XmlPullParser.START_TAG
+                        && "shared_bookmark".equals(parser.getName())) {
+                    urlStore.setShared(true);
+            }
+            else if (eventType == XmlPullParser.END_TAG && "url".equals(parser.getName())) {
+                done = true;
+            }
+        }
+        return urlStore;
+    }
+
+    private static BookmarkedConference getConferenceStorage(XmlPullParser parser) throws Exception {
+        String name = parser.getAttributeValue("", "name");
+        String autojoin = parser.getAttributeValue("", "autojoin");
+        String jid = parser.getAttributeValue("", "jid");
+
+        BookmarkedConference conf = new BookmarkedConference(jid);
+        conf.setName(name);
+        conf.setAutoJoin(Boolean.valueOf(autojoin).booleanValue());
+
+        // Check for nickname
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG && "nick".equals(parser.getName())) {
+                conf.setNickname(parser.nextText());
+            }
+            else if (eventType == XmlPullParser.START_TAG && "password".equals(parser.getName())) {
+                conf.setPassword(parser.nextText());
+            }
+            else if(eventType == XmlPullParser.START_TAG
+                        && "shared_bookmark".equals(parser.getName())) {
+                    conf.setShared(true);
+            }
+            else if (eventType == XmlPullParser.END_TAG && "conference".equals(parser.getName())) {
+                done = true;
+            }
+        }
+
+
+        return conf;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/bookmark/SharedBookmark.java b/src/org/jivesoftware/smackx/bookmark/SharedBookmark.java
new file mode 100644
index 0000000..f672bc1
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bookmark/SharedBookmark.java
@@ -0,0 +1,35 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.bookmark;
+
+/**
+ *  Interface to indicate if a bookmark is shared across the server.
+ *
+ * @author Alexander Wenckus
+ */
+public interface SharedBookmark {
+
+    /**
+     * Returns true if this bookmark is shared.
+     *
+     * @return returns true if this bookmark is shared.
+     */
+    public boolean isShared();
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/BytestreamListener.java b/src/org/jivesoftware/smackx/bytestreams/BytestreamListener.java
new file mode 100644
index 0000000..be78255
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/BytestreamListener.java
@@ -0,0 +1,47 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams;
+
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamListener;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager;
+
+/**
+ * BytestreamListener are notified if a remote user wants to initiate a bytestream. Implement this
+ * interface to handle incoming bytestream requests.
+ * <p>
+ * BytestreamListener can be registered at the {@link Socks5BytestreamManager} or the
+ * {@link InBandBytestreamManager}.
+ * <p>
+ * There are two ways to add this listener. See
+ * {@link BytestreamManager#addIncomingBytestreamListener(BytestreamListener)} and
+ * {@link BytestreamManager#addIncomingBytestreamListener(BytestreamListener, String)} for further
+ * details.
+ * <p>
+ * {@link Socks5BytestreamListener} or {@link InBandBytestreamListener} provide a more specific
+ * interface of the BytestreamListener.
+ * 
+ * @author Henning Staib
+ */
+public interface BytestreamListener {
+
+    /**
+     * This listener is notified if a bytestream request from another user has been received.
+     * 
+     * @param request the incoming bytestream request
+     */
+    public void incomingBytestreamRequest(BytestreamRequest request);
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/BytestreamManager.java b/src/org/jivesoftware/smackx/bytestreams/BytestreamManager.java
new file mode 100644
index 0000000..ca6bbc6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/BytestreamManager.java
@@ -0,0 +1,114 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams;
+
+import java.io.IOException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager;
+
+/**
+ * BytestreamManager provides a generic interface for bytestream managers.
+ * <p>
+ * There are two implementations of the interface. See {@link Socks5BytestreamManager} and
+ * {@link InBandBytestreamManager}.
+ * 
+ * @author Henning Staib
+ */
+public interface BytestreamManager {
+
+    /**
+     * Adds {@link BytestreamListener} that is called for every incoming bytestream request unless
+     * there is a user specific {@link BytestreamListener} registered.
+     * <p>
+     * See {@link Socks5BytestreamManager#addIncomingBytestreamListener(BytestreamListener)} and
+     * {@link InBandBytestreamManager#addIncomingBytestreamListener(BytestreamListener)} for further
+     * details.
+     * 
+     * @param listener the listener to register
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener);
+
+    /**
+     * Removes the given listener from the list of listeners for all incoming bytestream requests.
+     * 
+     * @param listener the listener to remove
+     */
+    public void removeIncomingBytestreamListener(BytestreamListener listener);
+
+    /**
+     * Adds {@link BytestreamListener} that is called for every incoming bytestream request unless
+     * there is a user specific {@link BytestreamListener} registered.
+     * <p>
+     * Use this method if you are awaiting an incoming bytestream request from a specific user.
+     * <p>
+     * See {@link Socks5BytestreamManager#addIncomingBytestreamListener(BytestreamListener, String)}
+     * and {@link InBandBytestreamManager#addIncomingBytestreamListener(BytestreamListener, String)}
+     * for further details.
+     * 
+     * @param listener the listener to register
+     * @param initiatorJID the JID of the user that wants to establish a bytestream
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener, String initiatorJID);
+
+    /**
+     * Removes the listener for the given user.
+     * 
+     * @param initiatorJID the JID of the user the listener should be removed
+     */
+    public void removeIncomingBytestreamListener(String initiatorJID);
+
+    /**
+     * Establishes a bytestream with the given user and returns the session to send/receive data
+     * to/from the user.
+     * <p>
+     * Use this method to establish bytestreams to users accepting all incoming bytestream requests
+     * since this method doesn't provide a way to tell the user something about the data to be sent.
+     * <p>
+     * To establish a bytestream after negotiation the kind of data to be sent (e.g. file transfer)
+     * use {@link #establishSession(String, String)}.
+     * <p>
+     * See {@link Socks5BytestreamManager#establishSession(String)} and
+     * {@link InBandBytestreamManager#establishSession(String)} for further details.
+     * 
+     * @param targetJID the JID of the user a bytestream should be established
+     * @return the session to send/receive data to/from the user
+     * @throws XMPPException if an error occurred while establishing the session
+     * @throws IOException if an IO error occurred while establishing the session
+     * @throws InterruptedException if the thread was interrupted while waiting in a blocking
+     *         operation
+     */
+    public BytestreamSession establishSession(String targetJID) throws XMPPException, IOException,
+                    InterruptedException;
+
+    /**
+     * Establishes a bytestream with the given user and returns the session to send/receive data
+     * to/from the user.
+     * <p>
+     * See {@link Socks5BytestreamManager#establishSession(String)} and
+     * {@link InBandBytestreamManager#establishSession(String)} for further details.
+     * 
+     * @param targetJID the JID of the user a bytestream should be established
+     * @param sessionID the session ID for the bytestream request
+     * @return the session to send/receive data to/from the user
+     * @throws XMPPException if an error occurred while establishing the session
+     * @throws IOException if an IO error occurred while establishing the session
+     * @throws InterruptedException if the thread was interrupted while waiting in a blocking
+     *         operation
+     */
+    public BytestreamSession establishSession(String targetJID, String sessionID)
+                    throws XMPPException, IOException, InterruptedException;
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java b/src/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java
new file mode 100644
index 0000000..e368bad
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/BytestreamRequest.java
@@ -0,0 +1,59 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamRequest;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamRequest;
+
+/**
+ * BytestreamRequest provides an interface to handle incoming bytestream requests.
+ * <p>
+ * There are two implementations of the interface. See {@link Socks5BytestreamRequest} and
+ * {@link InBandBytestreamRequest}.
+ * 
+ * @author Henning Staib
+ */
+public interface BytestreamRequest {
+
+    /**
+     * Returns the sender of the bytestream open request.
+     * 
+     * @return the sender of the bytestream open request
+     */
+    public String getFrom();
+
+    /**
+     * Returns the session ID of the bytestream open request.
+     * 
+     * @return the session ID of the bytestream open request
+     */
+    public String getSessionID();
+
+    /**
+     * Accepts the bytestream open request and returns the session to send/receive data.
+     * 
+     * @return the session to send/receive data
+     * @throws XMPPException if an error occurred while accepting the bytestream request
+     * @throws InterruptedException if the thread was interrupted while waiting in a blocking
+     *         operation
+     */
+    public BytestreamSession accept() throws XMPPException, InterruptedException;
+
+    /**
+     * Rejects the bytestream request by sending a reject error to the initiator.
+     */
+    public void reject();
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/BytestreamSession.java b/src/org/jivesoftware/smackx/bytestreams/BytestreamSession.java
new file mode 100644
index 0000000..7aafc35
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/BytestreamSession.java
@@ -0,0 +1,81 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamSession;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamSession;
+
+/**
+ * BytestreamSession provides an interface for established bytestream sessions.
+ * <p>
+ * There are two implementations of the interface. See {@link Socks5BytestreamSession} and
+ * {@link InBandBytestreamSession}.
+ * 
+ * @author Henning Staib
+ */
+public interface BytestreamSession {
+
+    /**
+     * Returns the InputStream associated with this session to send data.
+     * 
+     * @return the InputStream associated with this session to send data
+     * @throws IOException if an error occurs while retrieving the input stream
+     */
+    public InputStream getInputStream() throws IOException;
+
+    /**
+     * Returns the OutputStream associated with this session to receive data.
+     * 
+     * @return the OutputStream associated with this session to receive data
+     * @throws IOException if an error occurs while retrieving the output stream
+     */
+    public OutputStream getOutputStream() throws IOException;
+
+    /**
+     * Closes the bytestream session.
+     * <p>
+     * Closing the session will also close the input stream and the output stream associated to this
+     * session.
+     * 
+     * @throws IOException if an error occurs while closing the session
+     */
+    public void close() throws IOException;
+
+    /**
+     * Returns the timeout for read operations of the input stream associated with this session. 0
+     * returns implies that the option is disabled (i.e., timeout of infinity). Default is 0.
+     * 
+     * @return the timeout for read operations
+     * @throws IOException if there is an error in the underlying protocol
+     */
+    public int getReadTimeout() throws IOException;
+
+    /**
+     * Sets the specified timeout, in milliseconds. With this option set to a non-zero timeout, a
+     * read() call on the input stream associated with this session will block for only this amount
+     * of time. If the timeout expires, a java.net.SocketTimeoutException is raised, though the
+     * session is still valid. The option must be enabled prior to entering the blocking operation
+     * to have effect. The timeout must be > 0. A timeout of zero is interpreted as an infinite
+     * timeout. Default is 0.
+     * 
+     * @param timeout the specified timeout, in milliseconds
+     * @throws IOException if there is an error in the underlying protocol
+     */
+    public void setReadTimeout(int timeout) throws IOException;
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/CloseListener.java b/src/org/jivesoftware/smackx/bytestreams/ibb/CloseListener.java
new file mode 100644
index 0000000..7690e95
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/CloseListener.java
@@ -0,0 +1,75 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.IQTypeFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Close;
+
+/**
+ * CloseListener handles all In-Band Bytestream close requests.
+ * <p>
+ * If a close request is received it looks if a stored In-Band Bytestream
+ * session exists and closes it. If no session with the given session ID exists
+ * an &lt;item-not-found/&gt; error is returned to the sender.
+ * 
+ * @author Henning Staib
+ */
+class CloseListener implements PacketListener {
+
+    /* manager containing the listeners and the XMPP connection */
+    private final InBandBytestreamManager manager;
+
+    /* packet filter for all In-Band Bytestream close requests */
+    private final PacketFilter closeFilter = new AndFilter(new PacketTypeFilter(
+                    Close.class), new IQTypeFilter(IQ.Type.SET));
+
+    /**
+     * Constructor.
+     * 
+     * @param manager the In-Band Bytestream manager
+     */
+    protected CloseListener(InBandBytestreamManager manager) {
+        this.manager = manager;
+    }
+
+    public void processPacket(Packet packet) {
+        Close closeRequest = (Close) packet;
+        InBandBytestreamSession ibbSession = this.manager.getSessions().get(
+                        closeRequest.getSessionID());
+        if (ibbSession == null) {
+            this.manager.replyItemNotFoundPacket(closeRequest);
+        }
+        else {
+            ibbSession.closeByPeer(closeRequest);
+            this.manager.getSessions().remove(closeRequest.getSessionID());
+        }
+
+    }
+
+    /**
+     * Returns the packet filter for In-Band Bytestream close requests.
+     * 
+     * @return the packet filter for In-Band Bytestream close requests
+     */
+    protected PacketFilter getFilter() {
+        return this.closeFilter;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/DataListener.java b/src/org/jivesoftware/smackx/bytestreams/ibb/DataListener.java
new file mode 100644
index 0000000..166c146
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/DataListener.java
@@ -0,0 +1,73 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Data;
+
+/**
+ * DataListener handles all In-Band Bytestream IQ stanzas containing a data
+ * packet extension that don't belong to an existing session.
+ * <p>
+ * If a data packet is received it looks if a stored In-Band Bytestream session
+ * exists. If no session with the given session ID exists an
+ * &lt;item-not-found/&gt; error is returned to the sender.
+ * <p>
+ * Data packets belonging to a running In-Band Bytestream session are processed
+ * by more specific listeners registered when an {@link InBandBytestreamSession}
+ * is created.
+ * 
+ * @author Henning Staib
+ */
+class DataListener implements PacketListener {
+
+    /* manager containing the listeners and the XMPP connection */
+    private final InBandBytestreamManager manager;
+
+    /* packet filter for all In-Band Bytestream data packets */
+    private final PacketFilter dataFilter = new AndFilter(
+                    new PacketTypeFilter(Data.class));
+
+    /**
+     * Constructor.
+     * 
+     * @param manager the In-Band Bytestream manager
+     */
+    public DataListener(InBandBytestreamManager manager) {
+        this.manager = manager;
+    }
+
+    public void processPacket(Packet packet) {
+        Data data = (Data) packet;
+        InBandBytestreamSession ibbSession = this.manager.getSessions().get(
+                        data.getDataPacketExtension().getSessionID());
+        if (ibbSession == null) {
+            this.manager.replyItemNotFoundPacket(data);
+        }
+    }
+
+    /**
+     * Returns the packet filter for In-Band Bytestream data packets.
+     * 
+     * @return the packet filter for In-Band Bytestream data packets
+     */
+    protected PacketFilter getFilter() {
+        return this.dataFilter;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamListener.java b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamListener.java
new file mode 100644
index 0000000..68791a6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamListener.java
@@ -0,0 +1,46 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.BytestreamRequest;
+
+/**
+ * InBandBytestreamListener are informed if a remote user wants to initiate an In-Band Bytestream.
+ * Implement this interface to handle incoming In-Band Bytestream requests.
+ * <p>
+ * There are two ways to add this listener. See
+ * {@link InBandBytestreamManager#addIncomingBytestreamListener(BytestreamListener)} and
+ * {@link InBandBytestreamManager#addIncomingBytestreamListener(BytestreamListener, String)} for
+ * further details.
+ * 
+ * @author Henning Staib
+ */
+public abstract class InBandBytestreamListener implements BytestreamListener {
+
+    
+    
+    public void incomingBytestreamRequest(BytestreamRequest request) {
+        incomingBytestreamRequest((InBandBytestreamRequest) request);
+    }
+
+    /**
+     * This listener is notified if an In-Band Bytestream request from another user has been
+     * received.
+     * 
+     * @param request the incoming In-Band Bytestream request
+     */
+    public abstract void incomingBytestreamRequest(InBandBytestreamRequest request);
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java
new file mode 100644
index 0000000..ef52531
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamManager.java
@@ -0,0 +1,546 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Random;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.AbstractConnectionListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.SyncPacketSend;
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.BytestreamManager;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+import org.jivesoftware.smackx.filetransfer.FileTransferManager;
+
+/**
+ * The InBandBytestreamManager class handles establishing In-Band Bytestreams as specified in the <a
+ * href="http://xmpp.org/extensions/xep-0047.html">XEP-0047</a>.
+ * <p>
+ * The In-Band Bytestreams (IBB) enables two entities to establish a virtual bytestream over which
+ * they can exchange Base64-encoded chunks of data over XMPP itself. It is the fall-back mechanism
+ * in case the Socks5 bytestream method of transferring data is not available.
+ * <p>
+ * There are two ways to send data over an In-Band Bytestream. It could either use IQ stanzas to
+ * send data packets or message stanzas. If IQ stanzas are used every data packet is acknowledged by
+ * the receiver. This is the recommended way to avoid possible rate-limiting penalties. Message
+ * stanzas are not acknowledged because most XMPP server implementation don't support stanza
+ * flow-control method like <a href="http://xmpp.org/extensions/xep-0079.html">Advanced Message
+ * Processing</a>. To set the stanza that should be used invoke {@link #setStanza(StanzaType)}.
+ * <p>
+ * To establish an In-Band Bytestream invoke the {@link #establishSession(String)} method. This will
+ * negotiate an in-band bytestream with the given target JID and return a session.
+ * <p>
+ * If a session ID for the In-Band Bytestream was already negotiated (e.g. while negotiating a file
+ * transfer) invoke {@link #establishSession(String, String)}.
+ * <p>
+ * To handle incoming In-Band Bytestream requests add an {@link InBandBytestreamListener} to the
+ * manager. There are two ways to add this listener. If you want to be informed about incoming
+ * In-Band Bytestreams from a specific user add the listener by invoking
+ * {@link #addIncomingBytestreamListener(BytestreamListener, String)}. If the listener should
+ * respond to all In-Band Bytestream requests invoke
+ * {@link #addIncomingBytestreamListener(BytestreamListener)}.
+ * <p>
+ * Note that the registered {@link InBandBytestreamListener} will NOT be notified on incoming
+ * In-Band bytestream requests sent in the context of <a
+ * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+ * {@link FileTransferManager})
+ * <p>
+ * If no {@link InBandBytestreamListener}s are registered, all incoming In-Band bytestream requests
+ * will be rejected by returning a &lt;not-acceptable/&gt; error to the initiator.
+ * 
+ * @author Henning Staib
+ */
+public class InBandBytestreamManager implements BytestreamManager {
+
+    /**
+     * Stanzas that can be used to encapsulate In-Band Bytestream data packets.
+     */
+    public enum StanzaType {
+
+        /**
+         * IQ stanza.
+         */
+        IQ,
+
+        /**
+         * Message stanza.
+         */
+        MESSAGE
+    }
+
+    /*
+     * create a new InBandBytestreamManager and register its shutdown listener on every established
+     * connection
+     */
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                final InBandBytestreamManager manager;
+                manager = InBandBytestreamManager.getByteStreamManager(connection);
+
+                // register shutdown listener
+                connection.addConnectionListener(new AbstractConnectionListener() {
+
+                    public void connectionClosed() {
+                        manager.disableService();
+                    }
+
+                });
+
+            }
+        });
+    }
+
+    /**
+     * The XMPP namespace of the In-Band Bytestream
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/ibb";
+
+    /**
+     * Maximum block size that is allowed for In-Band Bytestreams
+     */
+    public static final int MAXIMUM_BLOCK_SIZE = 65535;
+
+    /* prefix used to generate session IDs */
+    private static final String SESSION_ID_PREFIX = "jibb_";
+
+    /* random generator to create session IDs */
+    private final static Random randomGenerator = new Random();
+
+    /* stores one InBandBytestreamManager for each XMPP connection */
+    private final static Map<Connection, InBandBytestreamManager> managers = new HashMap<Connection, InBandBytestreamManager>();
+
+    /* XMPP connection */
+    private final Connection connection;
+
+    /*
+     * assigns a user to a listener that is informed if an In-Band Bytestream request for this user
+     * is received
+     */
+    private final Map<String, BytestreamListener> userListeners = new ConcurrentHashMap<String, BytestreamListener>();
+
+    /*
+     * list of listeners that respond to all In-Band Bytestream requests if there are no user
+     * specific listeners for that request
+     */
+    private final List<BytestreamListener> allRequestListeners = Collections.synchronizedList(new LinkedList<BytestreamListener>());
+
+    /* listener that handles all incoming In-Band Bytestream requests */
+    private final InitiationListener initiationListener;
+
+    /* listener that handles all incoming In-Band Bytestream IQ data packets */
+    private final DataListener dataListener;
+
+    /* listener that handles all incoming In-Band Bytestream close requests */
+    private final CloseListener closeListener;
+
+    /* assigns a session ID to the In-Band Bytestream session */
+    private final Map<String, InBandBytestreamSession> sessions = new ConcurrentHashMap<String, InBandBytestreamSession>();
+
+    /* block size used for new In-Band Bytestreams */
+    private int defaultBlockSize = 4096;
+
+    /* maximum block size allowed for this connection */
+    private int maximumBlockSize = MAXIMUM_BLOCK_SIZE;
+
+    /* the stanza used to send data packets */
+    private StanzaType stanza = StanzaType.IQ;
+
+    /*
+     * list containing session IDs of In-Band Bytestream open packets that should be ignored by the
+     * InitiationListener
+     */
+    private List<String> ignoredBytestreamRequests = Collections.synchronizedList(new LinkedList<String>());
+
+    /**
+     * Returns the InBandBytestreamManager to handle In-Band Bytestreams for a given
+     * {@link Connection}.
+     * 
+     * @param connection the XMPP connection
+     * @return the InBandBytestreamManager for the given XMPP connection
+     */
+    public static synchronized InBandBytestreamManager getByteStreamManager(Connection connection) {
+        if (connection == null)
+            return null;
+        InBandBytestreamManager manager = managers.get(connection);
+        if (manager == null) {
+            manager = new InBandBytestreamManager(connection);
+            managers.put(connection, manager);
+        }
+        return manager;
+    }
+
+    /**
+     * Constructor.
+     * 
+     * @param connection the XMPP connection
+     */
+    private InBandBytestreamManager(Connection connection) {
+        this.connection = connection;
+
+        // register bytestream open packet listener
+        this.initiationListener = new InitiationListener(this);
+        this.connection.addPacketListener(this.initiationListener,
+                        this.initiationListener.getFilter());
+
+        // register bytestream data packet listener
+        this.dataListener = new DataListener(this);
+        this.connection.addPacketListener(this.dataListener, this.dataListener.getFilter());
+
+        // register bytestream close packet listener
+        this.closeListener = new CloseListener(this);
+        this.connection.addPacketListener(this.closeListener, this.closeListener.getFilter());
+
+    }
+
+    /**
+     * Adds InBandBytestreamListener that is called for every incoming in-band bytestream request
+     * unless there is a user specific InBandBytestreamListener registered.
+     * <p>
+     * If no listeners are registered all In-Band Bytestream request are rejected with a
+     * &lt;not-acceptable/&gt; error.
+     * <p>
+     * Note that the registered {@link InBandBytestreamListener} will NOT be notified on incoming
+     * Socks5 bytestream requests sent in the context of <a
+     * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+     * {@link FileTransferManager})
+     * 
+     * @param listener the listener to register
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener) {
+        this.allRequestListeners.add(listener);
+    }
+
+    /**
+     * Removes the given listener from the list of listeners for all incoming In-Band Bytestream
+     * requests.
+     * 
+     * @param listener the listener to remove
+     */
+    public void removeIncomingBytestreamListener(BytestreamListener listener) {
+        this.allRequestListeners.remove(listener);
+    }
+
+    /**
+     * Adds InBandBytestreamListener that is called for every incoming in-band bytestream request
+     * from the given user.
+     * <p>
+     * Use this method if you are awaiting an incoming Socks5 bytestream request from a specific
+     * user.
+     * <p>
+     * If no listeners are registered all In-Band Bytestream request are rejected with a
+     * &lt;not-acceptable/&gt; error.
+     * <p>
+     * Note that the registered {@link InBandBytestreamListener} will NOT be notified on incoming
+     * Socks5 bytestream requests sent in the context of <a
+     * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+     * {@link FileTransferManager})
+     * 
+     * @param listener the listener to register
+     * @param initiatorJID the JID of the user that wants to establish an In-Band Bytestream
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener, String initiatorJID) {
+        this.userListeners.put(initiatorJID, listener);
+    }
+
+    /**
+     * Removes the listener for the given user.
+     * 
+     * @param initiatorJID the JID of the user the listener should be removed
+     */
+    public void removeIncomingBytestreamListener(String initiatorJID) {
+        this.userListeners.remove(initiatorJID);
+    }
+
+    /**
+     * Use this method to ignore the next incoming In-Band Bytestream request containing the given
+     * session ID. No listeners will be notified for this request and and no error will be returned
+     * to the initiator.
+     * <p>
+     * This method should be used if you are awaiting an In-Band Bytestream request as a reply to
+     * another packet (e.g. file transfer).
+     * 
+     * @param sessionID to be ignored
+     */
+    public void ignoreBytestreamRequestOnce(String sessionID) {
+        this.ignoredBytestreamRequests.add(sessionID);
+    }
+
+    /**
+     * Returns the default block size that is used for all outgoing in-band bytestreams for this
+     * connection.
+     * <p>
+     * The recommended default block size is 4096 bytes. See <a
+     * href="http://xmpp.org/extensions/xep-0047.html#usage">XEP-0047</a> Section 5.
+     * 
+     * @return the default block size
+     */
+    public int getDefaultBlockSize() {
+        return defaultBlockSize;
+    }
+
+    /**
+     * Sets the default block size that is used for all outgoing in-band bytestreams for this
+     * connection.
+     * <p>
+     * The default block size must be between 1 and 65535 bytes. The recommended default block size
+     * is 4096 bytes. See <a href="http://xmpp.org/extensions/xep-0047.html#usage">XEP-0047</a>
+     * Section 5.
+     * 
+     * @param defaultBlockSize the default block size to set
+     */
+    public void setDefaultBlockSize(int defaultBlockSize) {
+        if (defaultBlockSize <= 0 || defaultBlockSize > MAXIMUM_BLOCK_SIZE) {
+            throw new IllegalArgumentException("Default block size must be between 1 and "
+                            + MAXIMUM_BLOCK_SIZE);
+        }
+        this.defaultBlockSize = defaultBlockSize;
+    }
+
+    /**
+     * Returns the maximum block size that is allowed for In-Band Bytestreams for this connection.
+     * <p>
+     * Incoming In-Band Bytestream open request will be rejected with an
+     * &lt;resource-constraint/&gt; error if the block size is greater then the maximum allowed
+     * block size.
+     * <p>
+     * The default maximum block size is 65535 bytes.
+     * 
+     * @return the maximum block size
+     */
+    public int getMaximumBlockSize() {
+        return maximumBlockSize;
+    }
+
+    /**
+     * Sets the maximum block size that is allowed for In-Band Bytestreams for this connection.
+     * <p>
+     * The maximum block size must be between 1 and 65535 bytes.
+     * <p>
+     * Incoming In-Band Bytestream open request will be rejected with an
+     * &lt;resource-constraint/&gt; error if the block size is greater then the maximum allowed
+     * block size.
+     * 
+     * @param maximumBlockSize the maximum block size to set
+     */
+    public void setMaximumBlockSize(int maximumBlockSize) {
+        if (maximumBlockSize <= 0 || maximumBlockSize > MAXIMUM_BLOCK_SIZE) {
+            throw new IllegalArgumentException("Maximum block size must be between 1 and "
+                            + MAXIMUM_BLOCK_SIZE);
+        }
+        this.maximumBlockSize = maximumBlockSize;
+    }
+
+    /**
+     * Returns the stanza used to send data packets.
+     * <p>
+     * Default is {@link StanzaType#IQ}. See <a
+     * href="http://xmpp.org/extensions/xep-0047.html#message">XEP-0047</a> Section 4.
+     * 
+     * @return the stanza used to send data packets
+     */
+    public StanzaType getStanza() {
+        return stanza;
+    }
+
+    /**
+     * Sets the stanza used to send data packets.
+     * <p>
+     * The use of {@link StanzaType#IQ} is recommended. See <a
+     * href="http://xmpp.org/extensions/xep-0047.html#message">XEP-0047</a> Section 4.
+     * 
+     * @param stanza the stanza to set
+     */
+    public void setStanza(StanzaType stanza) {
+        this.stanza = stanza;
+    }
+
+    /**
+     * Establishes an In-Band Bytestream with the given user and returns the session to send/receive
+     * data to/from the user.
+     * <p>
+     * Use this method to establish In-Band Bytestreams to users accepting all incoming In-Band
+     * Bytestream requests since this method doesn't provide a way to tell the user something about
+     * the data to be sent.
+     * <p>
+     * To establish an In-Band Bytestream after negotiation the kind of data to be sent (e.g. file
+     * transfer) use {@link #establishSession(String, String)}.
+     * 
+     * @param targetJID the JID of the user an In-Band Bytestream should be established
+     * @return the session to send/receive data to/from the user
+     * @throws XMPPException if the user doesn't support or accept in-band bytestreams, or if the
+     *         user prefers smaller block sizes
+     */
+    public InBandBytestreamSession establishSession(String targetJID) throws XMPPException {
+        String sessionID = getNextSessionID();
+        return establishSession(targetJID, sessionID);
+    }
+
+    /**
+     * Establishes an In-Band Bytestream with the given user using the given session ID and returns
+     * the session to send/receive data to/from the user.
+     * 
+     * @param targetJID the JID of the user an In-Band Bytestream should be established
+     * @param sessionID the session ID for the In-Band Bytestream request
+     * @return the session to send/receive data to/from the user
+     * @throws XMPPException if the user doesn't support or accept in-band bytestreams, or if the
+     *         user prefers smaller block sizes
+     */
+    public InBandBytestreamSession establishSession(String targetJID, String sessionID)
+                    throws XMPPException {
+        Open byteStreamRequest = new Open(sessionID, this.defaultBlockSize, this.stanza);
+        byteStreamRequest.setTo(targetJID);
+
+        // sending packet will throw exception on timeout or error reply
+        SyncPacketSend.getReply(this.connection, byteStreamRequest);
+
+        InBandBytestreamSession inBandBytestreamSession = new InBandBytestreamSession(
+                        this.connection, byteStreamRequest, targetJID);
+        this.sessions.put(sessionID, inBandBytestreamSession);
+
+        return inBandBytestreamSession;
+    }
+
+    /**
+     * Responses to the given IQ packet's sender with an XMPP error that an In-Band Bytestream is
+     * not accepted.
+     * 
+     * @param request IQ packet that should be answered with a not-acceptable error
+     */
+    protected void replyRejectPacket(IQ request) {
+        XMPPError xmppError = new XMPPError(XMPPError.Condition.no_acceptable);
+        IQ error = IQ.createErrorResponse(request, xmppError);
+        this.connection.sendPacket(error);
+    }
+
+    /**
+     * Responses to the given IQ packet's sender with an XMPP error that an In-Band Bytestream open
+     * request is rejected because its block size is greater than the maximum allowed block size.
+     * 
+     * @param request IQ packet that should be answered with a resource-constraint error
+     */
+    protected void replyResourceConstraintPacket(IQ request) {
+        XMPPError xmppError = new XMPPError(XMPPError.Condition.resource_constraint);
+        IQ error = IQ.createErrorResponse(request, xmppError);
+        this.connection.sendPacket(error);
+    }
+
+    /**
+     * Responses to the given IQ packet's sender with an XMPP error that an In-Band Bytestream
+     * session could not be found.
+     * 
+     * @param request IQ packet that should be answered with a item-not-found error
+     */
+    protected void replyItemNotFoundPacket(IQ request) {
+        XMPPError xmppError = new XMPPError(XMPPError.Condition.item_not_found);
+        IQ error = IQ.createErrorResponse(request, xmppError);
+        this.connection.sendPacket(error);
+    }
+
+    /**
+     * Returns a new unique session ID.
+     * 
+     * @return a new unique session ID
+     */
+    private String getNextSessionID() {
+        StringBuilder buffer = new StringBuilder();
+        buffer.append(SESSION_ID_PREFIX);
+        buffer.append(Math.abs(randomGenerator.nextLong()));
+        return buffer.toString();
+    }
+
+    /**
+     * Returns the XMPP connection.
+     * 
+     * @return the XMPP connection
+     */
+    protected Connection getConnection() {
+        return this.connection;
+    }
+
+    /**
+     * Returns the {@link InBandBytestreamListener} that should be informed if a In-Band Bytestream
+     * request from the given initiator JID is received.
+     * 
+     * @param initiator the initiator's JID
+     * @return the listener
+     */
+    protected BytestreamListener getUserListener(String initiator) {
+        return this.userListeners.get(initiator);
+    }
+
+    /**
+     * Returns a list of {@link InBandBytestreamListener} that are informed if there are no
+     * listeners for a specific initiator.
+     * 
+     * @return list of listeners
+     */
+    protected List<BytestreamListener> getAllRequestListeners() {
+        return this.allRequestListeners;
+    }
+
+    /**
+     * Returns the sessions map.
+     * 
+     * @return the sessions map
+     */
+    protected Map<String, InBandBytestreamSession> getSessions() {
+        return sessions;
+    }
+
+    /**
+     * Returns the list of session IDs that should be ignored by the InitialtionListener
+     * 
+     * @return list of session IDs
+     */
+    protected List<String> getIgnoredBytestreamRequests() {
+        return ignoredBytestreamRequests;
+    }
+
+    /**
+     * Disables the InBandBytestreamManager by removing its packet listeners and resetting its
+     * internal status.
+     */
+    private void disableService() {
+
+        // remove manager from static managers map
+        managers.remove(connection);
+
+        // remove all listeners registered by this manager
+        this.connection.removePacketListener(this.initiationListener);
+        this.connection.removePacketListener(this.dataListener);
+        this.connection.removePacketListener(this.closeListener);
+
+        // shutdown threads
+        this.initiationListener.shutdown();
+
+        // reset internal status
+        this.userListeners.clear();
+        this.allRequestListeners.clear();
+        this.sessions.clear();
+        this.ignoredBytestreamRequests.clear();
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java
new file mode 100644
index 0000000..5bc689a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamRequest.java
@@ -0,0 +1,92 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.bytestreams.BytestreamRequest;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+
+/**
+ * InBandBytestreamRequest class handles incoming In-Band Bytestream requests.
+ * 
+ * @author Henning Staib
+ */
+public class InBandBytestreamRequest implements BytestreamRequest {
+
+    /* the bytestream initialization request */
+    private final Open byteStreamRequest;
+
+    /*
+     * In-Band Bytestream manager containing the XMPP connection and helper
+     * methods
+     */
+    private final InBandBytestreamManager manager;
+
+    protected InBandBytestreamRequest(InBandBytestreamManager manager,
+                    Open byteStreamRequest) {
+        this.manager = manager;
+        this.byteStreamRequest = byteStreamRequest;
+    }
+
+    /**
+     * Returns the sender of the In-Band Bytestream open request.
+     * 
+     * @return the sender of the In-Band Bytestream open request
+     */
+    public String getFrom() {
+        return this.byteStreamRequest.getFrom();
+    }
+
+    /**
+     * Returns the session ID of the In-Band Bytestream open request.
+     * 
+     * @return the session ID of the In-Band Bytestream open request
+     */
+    public String getSessionID() {
+        return this.byteStreamRequest.getSessionID();
+    }
+
+    /**
+     * Accepts the In-Band Bytestream open request and returns the session to
+     * send/receive data.
+     * 
+     * @return the session to send/receive data
+     * @throws XMPPException if stream is invalid.
+     */
+    public InBandBytestreamSession accept() throws XMPPException {
+        Connection connection = this.manager.getConnection();
+
+        // create In-Band Bytestream session and store it
+        InBandBytestreamSession ibbSession = new InBandBytestreamSession(connection,
+                        this.byteStreamRequest, this.byteStreamRequest.getFrom());
+        this.manager.getSessions().put(this.byteStreamRequest.getSessionID(), ibbSession);
+
+        // acknowledge request
+        IQ resultIQ = IQ.createResultIQ(this.byteStreamRequest);
+        connection.sendPacket(resultIQ);
+
+        return ibbSession;
+    }
+
+    /**
+     * Rejects the In-Band Bytestream request by sending a reject error to the
+     * initiator.
+     */
+    public void reject() {
+        this.manager.replyRejectPacket(this.byteStreamRequest);
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java
new file mode 100644
index 0000000..a33682c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/InBandBytestreamSession.java
@@ -0,0 +1,795 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.SocketTimeoutException;
+import java.util.concurrent.BlockingQueue;
+import java.util.concurrent.LinkedBlockingQueue;
+import java.util.concurrent.TimeUnit;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smack.util.SyncPacketSend;
+import org.jivesoftware.smackx.bytestreams.BytestreamSession;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Close;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Data;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.DataPacketExtension;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+
+/**
+ * InBandBytestreamSession class represents an In-Band Bytestream session.
+ * <p>
+ * In-band bytestreams are bidirectional and this session encapsulates the streams for both
+ * directions.
+ * <p>
+ * Note that closing the In-Band Bytestream session will close both streams. If both streams are
+ * closed individually the session will be closed automatically once the second stream is closed.
+ * Use the {@link #setCloseBothStreamsEnabled(boolean)} method if both streams should be closed
+ * automatically if one of them is closed.
+ * 
+ * @author Henning Staib
+ */
+public class InBandBytestreamSession implements BytestreamSession {
+
+    /* XMPP connection */
+    private final Connection connection;
+
+    /* the In-Band Bytestream open request for this session */
+    private final Open byteStreamRequest;
+
+    /*
+     * the input stream for this session (either IQIBBInputStream or MessageIBBInputStream)
+     */
+    private IBBInputStream inputStream;
+
+    /*
+     * the output stream for this session (either IQIBBOutputStream or MessageIBBOutputStream)
+     */
+    private IBBOutputStream outputStream;
+
+    /* JID of the remote peer */
+    private String remoteJID;
+
+    /* flag to close both streams if one of them is closed */
+    private boolean closeBothStreamsEnabled = false;
+
+    /* flag to indicate if session is closed */
+    private boolean isClosed = false;
+
+    /**
+     * Constructor.
+     * 
+     * @param connection the XMPP connection
+     * @param byteStreamRequest the In-Band Bytestream open request for this session
+     * @param remoteJID JID of the remote peer
+     */
+    protected InBandBytestreamSession(Connection connection, Open byteStreamRequest,
+                    String remoteJID) {
+        this.connection = connection;
+        this.byteStreamRequest = byteStreamRequest;
+        this.remoteJID = remoteJID;
+
+        // initialize streams dependent to the uses stanza type
+        switch (byteStreamRequest.getStanza()) {
+        case IQ:
+            this.inputStream = new IQIBBInputStream();
+            this.outputStream = new IQIBBOutputStream();
+            break;
+        case MESSAGE:
+            this.inputStream = new MessageIBBInputStream();
+            this.outputStream = new MessageIBBOutputStream();
+            break;
+        }
+
+    }
+
+    public InputStream getInputStream() {
+        return this.inputStream;
+    }
+
+    public OutputStream getOutputStream() {
+        return this.outputStream;
+    }
+
+    public int getReadTimeout() {
+        return this.inputStream.readTimeout;
+    }
+
+    public void setReadTimeout(int timeout) {
+        if (timeout < 0) {
+            throw new IllegalArgumentException("Timeout must be >= 0");
+        }
+        this.inputStream.readTimeout = timeout;
+    }
+
+    /**
+     * Returns whether both streams should be closed automatically if one of the streams is closed.
+     * Default is <code>false</code>.
+     * 
+     * @return <code>true</code> if both streams will be closed if one of the streams is closed,
+     *         <code>false</code> if both streams can be closed independently.
+     */
+    public boolean isCloseBothStreamsEnabled() {
+        return closeBothStreamsEnabled;
+    }
+
+    /**
+     * Sets whether both streams should be closed automatically if one of the streams is closed.
+     * Default is <code>false</code>.
+     * 
+     * @param closeBothStreamsEnabled <code>true</code> if both streams should be closed if one of
+     *        the streams is closed, <code>false</code> if both streams should be closed
+     *        independently
+     */
+    public void setCloseBothStreamsEnabled(boolean closeBothStreamsEnabled) {
+        this.closeBothStreamsEnabled = closeBothStreamsEnabled;
+    }
+
+    public void close() throws IOException {
+        closeByLocal(true); // close input stream
+        closeByLocal(false); // close output stream
+    }
+
+    /**
+     * This method is invoked if a request to close the In-Band Bytestream has been received.
+     * 
+     * @param closeRequest the close request from the remote peer
+     */
+    protected void closeByPeer(Close closeRequest) {
+
+        /*
+         * close streams without flushing them, because stream is already considered closed on the
+         * remote peers side
+         */
+        this.inputStream.closeInternal();
+        this.inputStream.cleanup();
+        this.outputStream.closeInternal(false);
+
+        // acknowledge close request
+        IQ confirmClose = IQ.createResultIQ(closeRequest);
+        this.connection.sendPacket(confirmClose);
+
+    }
+
+    /**
+     * This method is invoked if one of the streams has been closed locally, if an error occurred
+     * locally or if the whole session should be closed.
+     * 
+     * @throws IOException if an error occurs while sending the close request
+     */
+    protected synchronized void closeByLocal(boolean in) throws IOException {
+        if (this.isClosed) {
+            return;
+        }
+
+        if (this.closeBothStreamsEnabled) {
+            this.inputStream.closeInternal();
+            this.outputStream.closeInternal(true);
+        }
+        else {
+            if (in) {
+                this.inputStream.closeInternal();
+            }
+            else {
+                // close stream but try to send any data left
+                this.outputStream.closeInternal(true);
+            }
+        }
+
+        if (this.inputStream.isClosed && this.outputStream.isClosed) {
+            this.isClosed = true;
+
+            // send close request
+            Close close = new Close(this.byteStreamRequest.getSessionID());
+            close.setTo(this.remoteJID);
+            try {
+                SyncPacketSend.getReply(this.connection, close);
+            }
+            catch (XMPPException e) {
+                throw new IOException("Error while closing stream: " + e.getMessage());
+            }
+
+            this.inputStream.cleanup();
+
+            // remove session from manager
+            InBandBytestreamManager.getByteStreamManager(this.connection).getSessions().remove(this);
+        }
+
+    }
+
+    /**
+     * IBBInputStream class is the base implementation of an In-Band Bytestream input stream.
+     * Subclasses of this input stream must provide a packet listener along with a packet filter to
+     * collect the In-Band Bytestream data packets.
+     */
+    private abstract class IBBInputStream extends InputStream {
+
+        /* the data packet listener to fill the data queue */
+        private final PacketListener dataPacketListener;
+
+        /* queue containing received In-Band Bytestream data packets */
+        protected final BlockingQueue<DataPacketExtension> dataQueue = new LinkedBlockingQueue<DataPacketExtension>();
+
+        /* buffer containing the data from one data packet */
+        private byte[] buffer;
+
+        /* pointer to the next byte to read from buffer */
+        private int bufferPointer = -1;
+
+        /* data packet sequence (range from 0 to 65535) */
+        private long seq = -1;
+
+        /* flag to indicate if input stream is closed */
+        private boolean isClosed = false;
+
+        /* flag to indicate if close method was invoked */
+        private boolean closeInvoked = false;
+
+        /* timeout for read operations */
+        private int readTimeout = 0;
+
+        /**
+         * Constructor.
+         */
+        public IBBInputStream() {
+            // add data packet listener to connection
+            this.dataPacketListener = getDataPacketListener();
+            connection.addPacketListener(this.dataPacketListener, getDataPacketFilter());
+        }
+
+        /**
+         * Returns the packet listener that processes In-Band Bytestream data packets.
+         * 
+         * @return the data packet listener
+         */
+        protected abstract PacketListener getDataPacketListener();
+
+        /**
+         * Returns the packet filter that accepts In-Band Bytestream data packets.
+         * 
+         * @return the data packet filter
+         */
+        protected abstract PacketFilter getDataPacketFilter();
+
+        public synchronized int read() throws IOException {
+            checkClosed();
+
+            // if nothing read yet or whole buffer has been read fill buffer
+            if (bufferPointer == -1 || bufferPointer >= buffer.length) {
+                // if no data available and stream was closed return -1
+                if (!loadBuffer()) {
+                    return -1;
+                }
+            }
+
+            // return byte and increment buffer pointer
+            return ((int) buffer[bufferPointer++]) & 0xff;
+        }
+
+        public synchronized int read(byte[] b, int off, int len) throws IOException {
+            if (b == null) {
+                throw new NullPointerException();
+            }
+            else if ((off < 0) || (off > b.length) || (len < 0) || ((off + len) > b.length)
+                            || ((off + len) < 0)) {
+                throw new IndexOutOfBoundsException();
+            }
+            else if (len == 0) {
+                return 0;
+            }
+
+            checkClosed();
+
+            // if nothing read yet or whole buffer has been read fill buffer
+            if (bufferPointer == -1 || bufferPointer >= buffer.length) {
+                // if no data available and stream was closed return -1
+                if (!loadBuffer()) {
+                    return -1;
+                }
+            }
+
+            // if more bytes wanted than available return all available
+            int bytesAvailable = buffer.length - bufferPointer;
+            if (len > bytesAvailable) {
+                len = bytesAvailable;
+            }
+
+            System.arraycopy(buffer, bufferPointer, b, off, len);
+            bufferPointer += len;
+            return len;
+        }
+
+        public synchronized int read(byte[] b) throws IOException {
+            return read(b, 0, b.length);
+        }
+
+        /**
+         * This method blocks until a data packet is received, the stream is closed or the current
+         * thread is interrupted.
+         * 
+         * @return <code>true</code> if data was received, otherwise <code>false</code>
+         * @throws IOException if data packets are out of sequence
+         */
+        private synchronized boolean loadBuffer() throws IOException {
+
+            // wait until data is available or stream is closed
+            DataPacketExtension data = null;
+            try {
+                if (this.readTimeout == 0) {
+                    while (data == null) {
+                        if (isClosed && this.dataQueue.isEmpty()) {
+                            return false;
+                        }
+                        data = this.dataQueue.poll(1000, TimeUnit.MILLISECONDS);
+                    }
+                }
+                else {
+                    data = this.dataQueue.poll(this.readTimeout, TimeUnit.MILLISECONDS);
+                    if (data == null) {
+                        throw new SocketTimeoutException();
+                    }
+                }
+            }
+            catch (InterruptedException e) {
+                // Restore the interrupted status
+                Thread.currentThread().interrupt();
+                return false;
+            }
+
+            // handle sequence overflow
+            if (this.seq == 65535) {
+                this.seq = -1;
+            }
+
+            // check if data packets sequence is successor of last seen sequence
+            long seq = data.getSeq();
+            if (seq - 1 != this.seq) {
+                // packets out of order; close stream/session
+                InBandBytestreamSession.this.close();
+                throw new IOException("Packets out of sequence");
+            }
+            else {
+                this.seq = seq;
+            }
+
+            // set buffer to decoded data
+            buffer = data.getDecodedData();
+            bufferPointer = 0;
+            return true;
+        }
+
+        /**
+         * Checks if this stream is closed and throws an IOException if necessary
+         * 
+         * @throws IOException if stream is closed and no data should be read anymore
+         */
+        private void checkClosed() throws IOException {
+            /* throw no exception if there is data available, but not if close method was invoked */
+            if ((isClosed && this.dataQueue.isEmpty()) || closeInvoked) {
+                // clear data queue in case additional data was received after stream was closed
+                this.dataQueue.clear();
+                throw new IOException("Stream is closed");
+            }
+        }
+
+        public boolean markSupported() {
+            return false;
+        }
+
+        public void close() throws IOException {
+            if (isClosed) {
+                return;
+            }
+
+            this.closeInvoked = true;
+
+            InBandBytestreamSession.this.closeByLocal(true);
+        }
+
+        /**
+         * This method sets the close flag and removes the data packet listener.
+         */
+        private void closeInternal() {
+            if (isClosed) {
+                return;
+            }
+            isClosed = true;
+        }
+
+        /**
+         * Invoked if the session is closed.
+         */
+        private void cleanup() {
+            connection.removePacketListener(this.dataPacketListener);
+        }
+
+    }
+
+    /**
+     * IQIBBInputStream class implements IBBInputStream to be used with IQ stanzas encapsulating the
+     * data packets.
+     */
+    private class IQIBBInputStream extends IBBInputStream {
+
+        protected PacketListener getDataPacketListener() {
+            return new PacketListener() {
+
+                private long lastSequence = -1;
+
+                public void processPacket(Packet packet) {
+                    // get data packet extension
+                    DataPacketExtension data = (DataPacketExtension) packet.getExtension(
+                                    DataPacketExtension.ELEMENT_NAME,
+                                    InBandBytestreamManager.NAMESPACE);
+
+                    /*
+                     * check if sequence was not used already (see XEP-0047 Section 2.2)
+                     */
+                    if (data.getSeq() <= this.lastSequence) {
+                        IQ unexpectedRequest = IQ.createErrorResponse((IQ) packet, new XMPPError(
+                                        XMPPError.Condition.unexpected_request));
+                        connection.sendPacket(unexpectedRequest);
+                        return;
+
+                    }
+
+                    // check if encoded data is valid (see XEP-0047 Section 2.2)
+                    if (data.getDecodedData() == null) {
+                        // data is invalid; respond with bad-request error
+                        IQ badRequest = IQ.createErrorResponse((IQ) packet, new XMPPError(
+                                        XMPPError.Condition.bad_request));
+                        connection.sendPacket(badRequest);
+                        return;
+                    }
+
+                    // data is valid; add to data queue
+                    dataQueue.offer(data);
+
+                    // confirm IQ
+                    IQ confirmData = IQ.createResultIQ((IQ) packet);
+                    connection.sendPacket(confirmData);
+
+                    // set last seen sequence
+                    this.lastSequence = data.getSeq();
+                    if (this.lastSequence == 65535) {
+                        this.lastSequence = -1;
+                    }
+
+                }
+
+            };
+        }
+
+        protected PacketFilter getDataPacketFilter() {
+            /*
+             * filter all IQ stanzas having type 'SET' (represented by Data class), containing a
+             * data packet extension, matching session ID and recipient
+             */
+            return new AndFilter(new PacketTypeFilter(Data.class), new IBBDataPacketFilter());
+        }
+
+    }
+
+    /**
+     * MessageIBBInputStream class implements IBBInputStream to be used with message stanzas
+     * encapsulating the data packets.
+     */
+    private class MessageIBBInputStream extends IBBInputStream {
+
+        protected PacketListener getDataPacketListener() {
+            return new PacketListener() {
+
+                public void processPacket(Packet packet) {
+                    // get data packet extension
+                    DataPacketExtension data = (DataPacketExtension) packet.getExtension(
+                                    DataPacketExtension.ELEMENT_NAME,
+                                    InBandBytestreamManager.NAMESPACE);
+
+                    // check if encoded data is valid
+                    if (data.getDecodedData() == null) {
+                        /*
+                         * TODO once a majority of XMPP server implementation support XEP-0079
+                         * Advanced Message Processing the invalid message could be answered with an
+                         * appropriate error. For now we just ignore the packet. Subsequent packets
+                         * with an increased sequence will cause the input stream to close the
+                         * stream/session.
+                         */
+                        return;
+                    }
+
+                    // data is valid; add to data queue
+                    dataQueue.offer(data);
+
+                    // TODO confirm packet once XMPP servers support XEP-0079
+                }
+
+            };
+        }
+
+        @Override
+        protected PacketFilter getDataPacketFilter() {
+            /*
+             * filter all message stanzas containing a data packet extension, matching session ID
+             * and recipient
+             */
+            return new AndFilter(new PacketTypeFilter(Message.class), new IBBDataPacketFilter());
+        }
+
+    }
+
+    /**
+     * IBBDataPacketFilter class filters all packets from the remote peer of this session,
+     * containing an In-Band Bytestream data packet extension whose session ID matches this sessions
+     * ID.
+     */
+    private class IBBDataPacketFilter implements PacketFilter {
+
+        public boolean accept(Packet packet) {
+            // sender equals remote peer
+            if (!packet.getFrom().equalsIgnoreCase(remoteJID)) {
+                return false;
+            }
+
+            // stanza contains data packet extension
+            PacketExtension packetExtension = packet.getExtension(DataPacketExtension.ELEMENT_NAME,
+                            InBandBytestreamManager.NAMESPACE);
+            if (packetExtension == null || !(packetExtension instanceof DataPacketExtension)) {
+                return false;
+            }
+
+            // session ID equals this session ID
+            DataPacketExtension data = (DataPacketExtension) packetExtension;
+            if (!data.getSessionID().equals(byteStreamRequest.getSessionID())) {
+                return false;
+            }
+
+            return true;
+        }
+
+    }
+
+    /**
+     * IBBOutputStream class is the base implementation of an In-Band Bytestream output stream.
+     * Subclasses of this output stream must provide a method to send data over XMPP stream.
+     */
+    private abstract class IBBOutputStream extends OutputStream {
+
+        /* buffer with the size of this sessions block size */
+        protected final byte[] buffer;
+
+        /* pointer to next byte to write to buffer */
+        protected int bufferPointer = 0;
+
+        /* data packet sequence (range from 0 to 65535) */
+        protected long seq = 0;
+
+        /* flag to indicate if output stream is closed */
+        protected boolean isClosed = false;
+
+        /**
+         * Constructor.
+         */
+        public IBBOutputStream() {
+            this.buffer = new byte[(byteStreamRequest.getBlockSize()/4)*3];
+        }
+
+        /**
+         * Writes the given data packet to the XMPP stream.
+         * 
+         * @param data the data packet
+         * @throws IOException if an I/O error occurred while sending or if the stream is closed
+         */
+        protected abstract void writeToXML(DataPacketExtension data) throws IOException;
+
+        public synchronized void write(int b) throws IOException {
+            if (this.isClosed) {
+                throw new IOException("Stream is closed");
+            }
+
+            // if buffer is full flush buffer
+            if (bufferPointer >= buffer.length) {
+                flushBuffer();
+            }
+
+            buffer[bufferPointer++] = (byte) b;
+        }
+
+        public synchronized void write(byte b[], int off, int len) throws IOException {
+            if (b == null) {
+                throw new NullPointerException();
+            }
+            else if ((off < 0) || (off > b.length) || (len < 0) || ((off + len) > b.length)
+                            || ((off + len) < 0)) {
+                throw new IndexOutOfBoundsException();
+            }
+            else if (len == 0) {
+                return;
+            }
+
+            if (this.isClosed) {
+                throw new IOException("Stream is closed");
+            }
+
+            // is data to send greater than buffer size
+            if (len >= buffer.length) {
+
+                // "byte" off the first chunk to write out
+                writeOut(b, off, buffer.length);
+
+                // recursively call this method with the lesser amount
+                write(b, off + buffer.length, len - buffer.length);
+            }
+            else {
+                writeOut(b, off, len);
+            }
+        }
+
+        public synchronized void write(byte[] b) throws IOException {
+            write(b, 0, b.length);
+        }
+
+        /**
+         * Fills the buffer with the given data and sends it over the XMPP stream if the buffers
+         * capacity has been reached. This method is only called from this class so it is assured
+         * that the amount of data to send is <= buffer capacity
+         * 
+         * @param b the data
+         * @param off the data
+         * @param len the number of bytes to write
+         * @throws IOException if an I/O error occurred while sending or if the stream is closed
+         */
+        private synchronized void writeOut(byte b[], int off, int len) throws IOException {
+            if (this.isClosed) {
+                throw new IOException("Stream is closed");
+            }
+
+            // set to 0 in case the next 'if' block is not executed
+            int available = 0;
+
+            // is data to send greater that buffer space left
+            if (len > buffer.length - bufferPointer) {
+                // fill buffer to capacity and send it
+                available = buffer.length - bufferPointer;
+                System.arraycopy(b, off, buffer, bufferPointer, available);
+                bufferPointer += available;
+                flushBuffer();
+            }
+
+            // copy the data left to buffer
+            System.arraycopy(b, off + available, buffer, bufferPointer, len - available);
+            bufferPointer += len - available;
+        }
+
+        public synchronized void flush() throws IOException {
+            if (this.isClosed) {
+                throw new IOException("Stream is closed");
+            }
+            flushBuffer();
+        }
+
+        private synchronized void flushBuffer() throws IOException {
+
+            // do nothing if no data to send available
+            if (bufferPointer == 0) {
+                return;
+            }
+
+            // create data packet
+            String enc = StringUtils.encodeBase64(buffer, 0, bufferPointer, false);
+            DataPacketExtension data = new DataPacketExtension(byteStreamRequest.getSessionID(),
+                            this.seq, enc);
+
+            // write to XMPP stream
+            writeToXML(data);
+
+            // reset buffer pointer
+            bufferPointer = 0;
+
+            // increment sequence, considering sequence overflow
+            this.seq = (this.seq + 1 == 65535 ? 0 : this.seq + 1);
+
+        }
+
+        public void close() throws IOException {
+            if (isClosed) {
+                return;
+            }
+            InBandBytestreamSession.this.closeByLocal(false);
+        }
+
+        /**
+         * Sets the close flag and optionally flushes the stream.
+         * 
+         * @param flush if <code>true</code> flushes the stream
+         */
+        protected void closeInternal(boolean flush) {
+            if (this.isClosed) {
+                return;
+            }
+            this.isClosed = true;
+
+            try {
+                if (flush) {
+                    flushBuffer();
+                }
+            }
+            catch (IOException e) {
+                /*
+                 * ignore, because writeToXML() will not throw an exception if stream is already
+                 * closed
+                 */
+            }
+        }
+
+    }
+
+    /**
+     * IQIBBOutputStream class implements IBBOutputStream to be used with IQ stanzas encapsulating
+     * the data packets.
+     */
+    private class IQIBBOutputStream extends IBBOutputStream {
+
+        @Override
+        protected synchronized void writeToXML(DataPacketExtension data) throws IOException {
+            // create IQ stanza containing data packet
+            IQ iq = new Data(data);
+            iq.setTo(remoteJID);
+
+            try {
+                SyncPacketSend.getReply(connection, iq);
+            }
+            catch (XMPPException e) {
+                // close session unless it is already closed
+                if (!this.isClosed) {
+                    InBandBytestreamSession.this.close();
+                    throw new IOException("Error while sending Data: " + e.getMessage());
+                }
+            }
+
+        }
+
+    }
+
+    /**
+     * MessageIBBOutputStream class implements IBBOutputStream to be used with message stanzas
+     * encapsulating the data packets.
+     */
+    private class MessageIBBOutputStream extends IBBOutputStream {
+
+        @Override
+        protected synchronized void writeToXML(DataPacketExtension data) {
+            // create message stanza containing data packet
+            Message message = new Message(remoteJID);
+            message.addExtension(data);
+
+            connection.sendPacket(message);
+
+        }
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/InitiationListener.java b/src/org/jivesoftware/smackx/bytestreams/ibb/InitiationListener.java
new file mode 100644
index 0000000..0ecb081
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/InitiationListener.java
@@ -0,0 +1,127 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb;
+
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.IQTypeFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+
+/**
+ * InitiationListener handles all incoming In-Band Bytestream open requests. If there are no
+ * listeners for a In-Band Bytestream request InitiationListener will always refuse the request and
+ * reply with a &lt;not-acceptable/&gt; error (<a
+ * href="http://xmpp.org/extensions/xep-0047.html#example-5" >XEP-0047</a> Section 2.1).
+ * <p>
+ * All In-Band Bytestream request having a block size greater than the maximum allowed block size
+ * for this connection are rejected with an &lt;resource-constraint/&gt; error. The maximum block
+ * size can be set by invoking {@link InBandBytestreamManager#setMaximumBlockSize(int)}.
+ * 
+ * @author Henning Staib
+ */
+class InitiationListener implements PacketListener {
+
+    /* manager containing the listeners and the XMPP connection */
+    private final InBandBytestreamManager manager;
+
+    /* packet filter for all In-Band Bytestream requests */
+    private final PacketFilter initFilter = new AndFilter(new PacketTypeFilter(Open.class),
+                    new IQTypeFilter(IQ.Type.SET));
+
+    /* executor service to process incoming requests concurrently */
+    private final ExecutorService initiationListenerExecutor;
+
+    /**
+     * Constructor.
+     * 
+     * @param manager the In-Band Bytestream manager
+     */
+    protected InitiationListener(InBandBytestreamManager manager) {
+        this.manager = manager;
+        initiationListenerExecutor = Executors.newCachedThreadPool();
+    }
+
+    public void processPacket(final Packet packet) {
+        initiationListenerExecutor.execute(new Runnable() {
+
+            public void run() {
+                processRequest(packet);
+            }
+        });
+    }
+
+    private void processRequest(Packet packet) {
+        Open ibbRequest = (Open) packet;
+
+        // validate that block size is within allowed range
+        if (ibbRequest.getBlockSize() > this.manager.getMaximumBlockSize()) {
+            this.manager.replyResourceConstraintPacket(ibbRequest);
+            return;
+        }
+
+        // ignore request if in ignore list
+        if (this.manager.getIgnoredBytestreamRequests().remove(ibbRequest.getSessionID()))
+            return;
+
+        // build bytestream request from packet
+        InBandBytestreamRequest request = new InBandBytestreamRequest(this.manager, ibbRequest);
+
+        // notify listeners for bytestream initiation from a specific user
+        BytestreamListener userListener = this.manager.getUserListener(ibbRequest.getFrom());
+        if (userListener != null) {
+            userListener.incomingBytestreamRequest(request);
+
+        }
+        else if (!this.manager.getAllRequestListeners().isEmpty()) {
+            /*
+             * if there is no user specific listener inform listeners for all initiation requests
+             */
+            for (BytestreamListener listener : this.manager.getAllRequestListeners()) {
+                listener.incomingBytestreamRequest(request);
+            }
+
+        }
+        else {
+            /*
+             * if there is no listener for this initiation request, reply with reject message
+             */
+            this.manager.replyRejectPacket(ibbRequest);
+        }
+    }
+
+    /**
+     * Returns the packet filter for In-Band Bytestream open requests.
+     * 
+     * @return the packet filter for In-Band Bytestream open requests
+     */
+    protected PacketFilter getFilter() {
+        return this.initFilter;
+    }
+
+    /**
+     * Shuts down the listeners executor service.
+     */
+    protected void shutdown() {
+        this.initiationListenerExecutor.shutdownNow();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Close.java b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Close.java
new file mode 100644
index 0000000..9a78d73
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Close.java
@@ -0,0 +1,65 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+
+/**
+ * Represents a request to close an In-Band Bytestream.
+ * 
+ * @author Henning Staib
+ */
+public class Close extends IQ {
+
+    /* unique session ID identifying this In-Band Bytestream */
+    private final String sessionID;
+
+    /**
+     * Creates a new In-Band Bytestream close request packet.
+     * 
+     * @param sessionID unique session ID identifying this In-Band Bytestream
+     */
+    public Close(String sessionID) {
+        if (sessionID == null || "".equals(sessionID)) {
+            throw new IllegalArgumentException("Session ID must not be null or empty");
+        }
+        this.sessionID = sessionID;
+        setType(Type.SET);
+    }
+
+    /**
+     * Returns the unique session ID identifying this In-Band Bytestream.
+     * 
+     * @return the unique session ID identifying this In-Band Bytestream
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    @Override
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<close ");
+        buf.append("xmlns=\"");
+        buf.append(InBandBytestreamManager.NAMESPACE);
+        buf.append("\" ");
+        buf.append("sid=\"");
+        buf.append(sessionID);
+        buf.append("\"");
+        buf.append("/>");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Data.java b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Data.java
new file mode 100644
index 0000000..696fa75
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Data.java
@@ -0,0 +1,64 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+/**
+ * Represents a chunk of data sent over an In-Band Bytestream encapsulated in an
+ * IQ stanza.
+ * 
+ * @author Henning Staib
+ */
+public class Data extends IQ {
+
+    /* the data packet extension */
+    private final DataPacketExtension dataPacketExtension;
+
+    /**
+     * Constructor.
+     * 
+     * @param data data packet extension containing the encoded data
+     */
+    public Data(DataPacketExtension data) {
+        if (data == null) {
+            throw new IllegalArgumentException("Data must not be null");
+        }
+        this.dataPacketExtension = data;
+
+        /*
+         * also set as packet extension so that data packet extension can be
+         * retrieved from IQ stanza and message stanza in the same way
+         */
+        addExtension(data);
+        setType(IQ.Type.SET);
+    }
+
+    /**
+     * Returns the data packet extension.
+     * <p>
+     * Convenience method for <code>packet.getExtension("data",
+     * "http://jabber.org/protocol/ibb")</code>.
+     * 
+     * @return the data packet extension
+     */
+    public DataPacketExtension getDataPacketExtension() {
+        return this.dataPacketExtension;
+    }
+
+    public String getChildElementXML() {
+        return this.dataPacketExtension.toXML();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/packet/DataPacketExtension.java b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/DataPacketExtension.java
new file mode 100644
index 0000000..80ed1e1
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/DataPacketExtension.java
@@ -0,0 +1,149 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+
+/**
+ * Represents a chunk of data of an In-Band Bytestream within an IQ stanza or a
+ * message stanza
+ * 
+ * @author Henning Staib
+ */
+public class DataPacketExtension implements PacketExtension {
+
+    /**
+     * The element name of the data packet extension.
+     */
+    public final static String ELEMENT_NAME = "data";
+
+    /* unique session ID identifying this In-Band Bytestream */
+    private final String sessionID;
+
+    /* sequence of this packet in regard to the other data packets */
+    private final long seq;
+
+    /* the data contained in this packet */
+    private final String data;
+
+    private byte[] decodedData;
+
+    /**
+     * Creates a new In-Band Bytestream data packet.
+     * 
+     * @param sessionID unique session ID identifying this In-Band Bytestream
+     * @param seq sequence of this packet in regard to the other data packets
+     * @param data the base64 encoded data contained in this packet
+     */
+    public DataPacketExtension(String sessionID, long seq, String data) {
+        if (sessionID == null || "".equals(sessionID)) {
+            throw new IllegalArgumentException("Session ID must not be null or empty");
+        }
+        if (seq < 0 || seq > 65535) {
+            throw new IllegalArgumentException("Sequence must not be between 0 and 65535");
+        }
+        if (data == null) {
+            throw new IllegalArgumentException("Data must not be null");
+        }
+        this.sessionID = sessionID;
+        this.seq = seq;
+        this.data = data;
+    }
+
+    /**
+     * Returns the unique session ID identifying this In-Band Bytestream.
+     * 
+     * @return the unique session ID identifying this In-Band Bytestream
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    /**
+     * Returns the sequence of this packet in regard to the other data packets.
+     * 
+     * @return the sequence of this packet in regard to the other data packets.
+     */
+    public long getSeq() {
+        return seq;
+    }
+
+    /**
+     * Returns the data contained in this packet.
+     * 
+     * @return the data contained in this packet.
+     */
+    public String getData() {
+        return data;
+    }
+
+    /**
+     * Returns the decoded data or null if data could not be decoded.
+     * <p>
+     * The encoded data is invalid if it contains bad Base64 input characters or
+     * if it contains the pad ('=') character on a position other than the last
+     * character(s) of the data. See <a
+     * href="http://xmpp.org/extensions/xep-0047.html#sec">XEP-0047</a> Section
+     * 6.
+     * 
+     * @return the decoded data
+     */
+    public byte[] getDecodedData() {
+        // return cached decoded data
+        if (this.decodedData != null) {
+            return this.decodedData;
+        }
+
+        // data must not contain the pad (=) other than end of data
+        if (data.matches(".*={1,2}+.+")) {
+            return null;
+        }
+
+        // decodeBase64 will return null if bad characters are included
+        this.decodedData = StringUtils.decodeBase64(data);
+        return this.decodedData;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return InBandBytestreamManager.NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<");
+        buf.append(getElementName());
+        buf.append(" ");
+        buf.append("xmlns=\"");
+        buf.append(InBandBytestreamManager.NAMESPACE);
+        buf.append("\" ");
+        buf.append("seq=\"");
+        buf.append(seq);
+        buf.append("\" ");
+        buf.append("sid=\"");
+        buf.append(sessionID);
+        buf.append("\">");
+        buf.append(data);
+        buf.append("</");
+        buf.append(getElementName());
+        buf.append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Open.java b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Open.java
new file mode 100644
index 0000000..94a7a9b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/packet/Open.java
@@ -0,0 +1,126 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager.StanzaType;
+
+/**
+ * Represents a request to open an In-Band Bytestream.
+ * 
+ * @author Henning Staib
+ */
+public class Open extends IQ {
+
+    /* unique session ID identifying this In-Band Bytestream */
+    private final String sessionID;
+
+    /* block size in which the data will be fragmented */
+    private final int blockSize;
+
+    /* stanza type used to encapsulate the data */
+    private final StanzaType stanza;
+
+    /**
+     * Creates a new In-Band Bytestream open request packet.
+     * <p>
+     * The data sent over this In-Band Bytestream will be fragmented in blocks
+     * with the given block size. The block size should not be greater than
+     * 65535. A recommended default value is 4096.
+     * <p>
+     * The data can be sent using IQ stanzas or message stanzas.
+     * 
+     * @param sessionID unique session ID identifying this In-Band Bytestream
+     * @param blockSize block size in which the data will be fragmented
+     * @param stanza stanza type used to encapsulate the data
+     */
+    public Open(String sessionID, int blockSize, StanzaType stanza) {
+        if (sessionID == null || "".equals(sessionID)) {
+            throw new IllegalArgumentException("Session ID must not be null or empty");
+        }
+        if (blockSize <= 0) {
+            throw new IllegalArgumentException("Block size must be greater than zero");
+        }
+
+        this.sessionID = sessionID;
+        this.blockSize = blockSize;
+        this.stanza = stanza;
+        setType(Type.SET);
+    }
+
+    /**
+     * Creates a new In-Band Bytestream open request packet.
+     * <p>
+     * The data sent over this In-Band Bytestream will be fragmented in blocks
+     * with the given block size. The block size should not be greater than
+     * 65535. A recommended default value is 4096.
+     * <p>
+     * The data will be sent using IQ stanzas.
+     * 
+     * @param sessionID unique session ID identifying this In-Band Bytestream
+     * @param blockSize block size in which the data will be fragmented
+     */
+    public Open(String sessionID, int blockSize) {
+        this(sessionID, blockSize, StanzaType.IQ);
+    }
+
+    /**
+     * Returns the unique session ID identifying this In-Band Bytestream.
+     * 
+     * @return the unique session ID identifying this In-Band Bytestream
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    /**
+     * Returns the block size in which the data will be fragmented.
+     * 
+     * @return the block size in which the data will be fragmented
+     */
+    public int getBlockSize() {
+        return blockSize;
+    }
+
+    /**
+     * Returns the stanza type used to encapsulate the data.
+     * 
+     * @return the stanza type used to encapsulate the data
+     */
+    public StanzaType getStanza() {
+        return stanza;
+    }
+
+    @Override
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<open ");
+        buf.append("xmlns=\"");
+        buf.append(InBandBytestreamManager.NAMESPACE);
+        buf.append("\" ");
+        buf.append("block-size=\"");
+        buf.append(blockSize);
+        buf.append("\" ");
+        buf.append("sid=\"");
+        buf.append(sessionID);
+        buf.append("\" ");
+        buf.append("stanza=\"");
+        buf.append(stanza.toString().toLowerCase());
+        buf.append("\"");
+        buf.append("/>");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/provider/CloseIQProvider.java b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/CloseIQProvider.java
new file mode 100644
index 0000000..566724c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/CloseIQProvider.java
@@ -0,0 +1,33 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Close;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses a close In-Band Bytestream packet.
+ * 
+ * @author Henning Staib
+ */
+public class CloseIQProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        String sid = parser.getAttributeValue("", "sid");
+        return new Close(sid);
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/provider/DataPacketProvider.java b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/DataPacketProvider.java
new file mode 100644
index 0000000..5abed08
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/DataPacketProvider.java
@@ -0,0 +1,45 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Data;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.DataPacketExtension;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses an In-Band Bytestream data packet which can be a packet extension of
+ * either an IQ stanza or a message stanza.
+ * 
+ * @author Henning Staib
+ */
+public class DataPacketProvider implements PacketExtensionProvider, IQProvider {
+
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        String sessionID = parser.getAttributeValue("", "sid");
+        long seq = Long.parseLong(parser.getAttributeValue("", "seq"));
+        String data = parser.nextText();
+        return new DataPacketExtension(sessionID, seq, data);
+    }
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        DataPacketExtension data = (DataPacketExtension) parseExtension(parser);
+        IQ iq = new Data(data);
+        return iq;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/ibb/provider/OpenIQProvider.java b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/OpenIQProvider.java
new file mode 100644
index 0000000..3cc725a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/ibb/provider/OpenIQProvider.java
@@ -0,0 +1,45 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.ibb.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager.StanzaType;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses an In-Band Bytestream open packet.
+ * 
+ * @author Henning Staib
+ */
+public class OpenIQProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        String sessionID = parser.getAttributeValue("", "sid");
+        int blockSize = Integer.parseInt(parser.getAttributeValue("", "block-size"));
+
+        String stanzaValue = parser.getAttributeValue("", "stanza");
+        StanzaType stanza = null;
+        if (stanzaValue == null) {
+            stanza = StanzaType.IQ;
+        }
+        else {
+            stanza = StanzaType.valueOf(stanzaValue.toUpperCase());
+        }
+
+        return new Open(sessionID, blockSize, stanza);
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/InitiationListener.java b/src/org/jivesoftware/smackx/bytestreams/socks5/InitiationListener.java
new file mode 100644
index 0000000..2a78250
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/InitiationListener.java
@@ -0,0 +1,119 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.IQTypeFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+
+/**
+ * InitiationListener handles all incoming SOCKS5 Bytestream initiation requests. If there are no
+ * listeners for a SOCKS5 bytestream request InitiationListener will always refuse the request and
+ * reply with a &lt;not-acceptable/&gt; error (<a
+ * href="http://xmpp.org/extensions/xep-0065.html#usecase-alternate">XEP-0065</a> Section 5.2.A2).
+ * 
+ * @author Henning Staib
+ */
+final class InitiationListener implements PacketListener {
+
+    /* manager containing the listeners and the XMPP connection */
+    private final Socks5BytestreamManager manager;
+
+    /* packet filter for all SOCKS5 Bytestream requests */
+    private final PacketFilter initFilter = new AndFilter(new PacketTypeFilter(Bytestream.class),
+                    new IQTypeFilter(IQ.Type.SET));
+
+    /* executor service to process incoming requests concurrently */
+    private final ExecutorService initiationListenerExecutor;
+
+    /**
+     * Constructor
+     * 
+     * @param manager the SOCKS5 Bytestream manager
+     */
+    protected InitiationListener(Socks5BytestreamManager manager) {
+        this.manager = manager;
+        initiationListenerExecutor = Executors.newCachedThreadPool();
+    }
+
+    public void processPacket(final Packet packet) {
+        initiationListenerExecutor.execute(new Runnable() {
+
+            public void run() {
+                processRequest(packet);
+            }
+        });
+    }
+
+    private void processRequest(Packet packet) {
+        Bytestream byteStreamRequest = (Bytestream) packet;
+
+        // ignore request if in ignore list
+        if (this.manager.getIgnoredBytestreamRequests().remove(byteStreamRequest.getSessionID())) {
+            return;
+        }
+
+        // build bytestream request from packet
+        Socks5BytestreamRequest request = new Socks5BytestreamRequest(this.manager,
+                        byteStreamRequest);
+
+        // notify listeners for bytestream initiation from a specific user
+        BytestreamListener userListener = this.manager.getUserListener(byteStreamRequest.getFrom());
+        if (userListener != null) {
+            userListener.incomingBytestreamRequest(request);
+
+        }
+        else if (!this.manager.getAllRequestListeners().isEmpty()) {
+            /*
+             * if there is no user specific listener inform listeners for all initiation requests
+             */
+            for (BytestreamListener listener : this.manager.getAllRequestListeners()) {
+                listener.incomingBytestreamRequest(request);
+            }
+
+        }
+        else {
+            /*
+             * if there is no listener for this initiation request, reply with reject message
+             */
+            this.manager.replyRejectPacket(byteStreamRequest);
+        }
+    }
+
+    /**
+     * Returns the packet filter for SOCKS5 Bytestream initialization requests.
+     * 
+     * @return the packet filter for SOCKS5 Bytestream initialization requests
+     */
+    protected PacketFilter getFilter() {
+        return this.initFilter;
+    }
+
+    /**
+     * Shuts down the listeners executor service.
+     */
+    protected void shutdown() {
+        this.initiationListenerExecutor.shutdownNow();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamListener.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamListener.java
new file mode 100644
index 0000000..1430b1d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamListener.java
@@ -0,0 +1,43 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.BytestreamRequest;
+
+/**
+ * Socks5BytestreamListener are informed if a remote user wants to initiate a SOCKS5 Bytestream.
+ * Implement this interface to handle incoming SOCKS5 Bytestream requests.
+ * <p>
+ * There are two ways to add this listener. See
+ * {@link Socks5BytestreamManager#addIncomingBytestreamListener(BytestreamListener)} and
+ * {@link Socks5BytestreamManager#addIncomingBytestreamListener(BytestreamListener, String)} for
+ * further details.
+ * 
+ * @author Henning Staib
+ */
+public abstract class Socks5BytestreamListener implements BytestreamListener {
+
+    public void incomingBytestreamRequest(BytestreamRequest request) {
+        incomingBytestreamRequest((Socks5BytestreamRequest) request);
+    }
+
+    /**
+     * This listener is notified if a SOCKS5 Bytestream request from another user has been received.
+     * 
+     * @param request the incoming SOCKS5 Bytestream request
+     */
+    public abstract void incomingBytestreamRequest(Socks5BytestreamRequest request);
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java
new file mode 100644
index 0000000..1383495
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamManager.java
@@ -0,0 +1,777 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.IOException;
+import java.lang.ref.WeakReference;
+import java.net.Socket;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Random;
+import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.TimeoutException;
+
+import org.jivesoftware.smack.AbstractConnectionListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.SyncPacketSend;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.bytestreams.BytestreamListener;
+import org.jivesoftware.smackx.bytestreams.BytestreamManager;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHostUsed;
+import org.jivesoftware.smackx.filetransfer.FileTransferManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+import org.jivesoftware.smackx.packet.DiscoverItems.Item;
+
+/**
+ * The Socks5BytestreamManager class handles establishing SOCKS5 Bytestreams as specified in the <a
+ * href="http://xmpp.org/extensions/xep-0065.html">XEP-0065</a>.
+ * <p>
+ * A SOCKS5 Bytestream is negotiated partly over the XMPP XML stream and partly over a separate
+ * socket. The actual transfer though takes place over a separately created socket.
+ * <p>
+ * A SOCKS5 Bytestream generally has three parties, the initiator, the target, and the stream host.
+ * The stream host is a specialized SOCKS5 proxy setup on a server, or, the initiator can act as the
+ * stream host.
+ * <p>
+ * To establish a SOCKS5 Bytestream invoke the {@link #establishSession(String)} method. This will
+ * negotiate a SOCKS5 Bytestream with the given target JID and return a socket.
+ * <p>
+ * If a session ID for the SOCKS5 Bytestream was already negotiated (e.g. while negotiating a file
+ * transfer) invoke {@link #establishSession(String, String)}.
+ * <p>
+ * To handle incoming SOCKS5 Bytestream requests add an {@link Socks5BytestreamListener} to the
+ * manager. There are two ways to add this listener. If you want to be informed about incoming
+ * SOCKS5 Bytestreams from a specific user add the listener by invoking
+ * {@link #addIncomingBytestreamListener(BytestreamListener, String)}. If the listener should
+ * respond to all SOCKS5 Bytestream requests invoke
+ * {@link #addIncomingBytestreamListener(BytestreamListener)}.
+ * <p>
+ * Note that the registered {@link Socks5BytestreamListener} will NOT be notified on incoming Socks5
+ * bytestream requests sent in the context of <a
+ * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+ * {@link FileTransferManager})
+ * <p>
+ * If no {@link Socks5BytestreamListener}s are registered, all incoming SOCKS5 Bytestream requests
+ * will be rejected by returning a &lt;not-acceptable/&gt; error to the initiator.
+ * 
+ * @author Henning Staib
+ */
+public final class Socks5BytestreamManager implements BytestreamManager {
+
+    /*
+     * create a new Socks5BytestreamManager and register a shutdown listener on every established
+     * connection
+     */
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+
+            public void connectionCreated(final Connection connection) {
+                final Socks5BytestreamManager manager;
+                manager = Socks5BytestreamManager.getBytestreamManager(connection);
+
+                // register shutdown listener
+                connection.addConnectionListener(new AbstractConnectionListener() {
+
+                    public void connectionClosed() {
+                        manager.disableService();
+                    }
+                    
+                    public void connectionClosedOnError(Exception e) {
+                        manager.disableService();
+                    }
+                    
+                    public void reconnectionSuccessful() {
+                        managers.put(connection, manager);
+                    }
+
+                });
+            }
+
+        });
+    }
+
+    /**
+     * The XMPP namespace of the SOCKS5 Bytestream
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/bytestreams";
+
+    /* prefix used to generate session IDs */
+    private static final String SESSION_ID_PREFIX = "js5_";
+
+    /* random generator to create session IDs */
+    private final static Random randomGenerator = new Random();
+
+    /* stores one Socks5BytestreamManager for each XMPP connection */
+    private final static Map<Connection, Socks5BytestreamManager> managers = new WeakHashMap<Connection, Socks5BytestreamManager>();
+
+    /* XMPP connection */
+    private final Connection connection;
+
+    /*
+     * assigns a user to a listener that is informed if a bytestream request for this user is
+     * received
+     */
+    private final Map<String, BytestreamListener> userListeners = new ConcurrentHashMap<String, BytestreamListener>();
+
+    /*
+     * list of listeners that respond to all bytestream requests if there are not user specific
+     * listeners for that request
+     */
+    private final List<BytestreamListener> allRequestListeners = Collections.synchronizedList(new LinkedList<BytestreamListener>());
+
+    /* listener that handles all incoming bytestream requests */
+    private final InitiationListener initiationListener;
+
+    /* timeout to wait for the response to the SOCKS5 Bytestream initialization request */
+    private int targetResponseTimeout = 10000;
+
+    /* timeout for connecting to the SOCKS5 proxy selected by the target */
+    private int proxyConnectionTimeout = 10000;
+
+    /* blacklist of errornous SOCKS5 proxies */
+    private final List<String> proxyBlacklist = Collections.synchronizedList(new LinkedList<String>());
+
+    /* remember the last proxy that worked to prioritize it */
+    private String lastWorkingProxy = null;
+
+    /* flag to enable/disable prioritization of last working proxy */
+    private boolean proxyPrioritizationEnabled = true;
+
+    /*
+     * list containing session IDs of SOCKS5 Bytestream initialization packets that should be
+     * ignored by the InitiationListener
+     */
+    private List<String> ignoredBytestreamRequests = Collections.synchronizedList(new LinkedList<String>());
+
+    /**
+     * Returns the Socks5BytestreamManager to handle SOCKS5 Bytestreams for a given
+     * {@link Connection}.
+     * <p>
+     * If no manager exists a new is created and initialized.
+     * 
+     * @param connection the XMPP connection or <code>null</code> if given connection is
+     *        <code>null</code>
+     * @return the Socks5BytestreamManager for the given XMPP connection
+     */
+    public static synchronized Socks5BytestreamManager getBytestreamManager(Connection connection) {
+        if (connection == null) {
+            return null;
+        }
+        Socks5BytestreamManager manager = managers.get(connection);
+        if (manager == null) {
+            manager = new Socks5BytestreamManager(connection);
+            managers.put(connection, manager);
+            manager.activate();
+        }
+        return manager;
+    }
+
+    /**
+     * Private constructor.
+     * 
+     * @param connection the XMPP connection
+     */
+    private Socks5BytestreamManager(Connection connection) {
+        this.connection = connection;
+        this.initiationListener = new InitiationListener(this);
+    }
+
+    /**
+     * Adds BytestreamListener that is called for every incoming SOCKS5 Bytestream request unless
+     * there is a user specific BytestreamListener registered.
+     * <p>
+     * If no listeners are registered all SOCKS5 Bytestream request are rejected with a
+     * &lt;not-acceptable/&gt; error.
+     * <p>
+     * Note that the registered {@link BytestreamListener} will NOT be notified on incoming Socks5
+     * bytestream requests sent in the context of <a
+     * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+     * {@link FileTransferManager})
+     * 
+     * @param listener the listener to register
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener) {
+        this.allRequestListeners.add(listener);
+    }
+
+    /**
+     * Removes the given listener from the list of listeners for all incoming SOCKS5 Bytestream
+     * requests.
+     * 
+     * @param listener the listener to remove
+     */
+    public void removeIncomingBytestreamListener(BytestreamListener listener) {
+        this.allRequestListeners.remove(listener);
+    }
+
+    /**
+     * Adds BytestreamListener that is called for every incoming SOCKS5 Bytestream request from the
+     * given user.
+     * <p>
+     * Use this method if you are awaiting an incoming SOCKS5 Bytestream request from a specific
+     * user.
+     * <p>
+     * If no listeners are registered all SOCKS5 Bytestream request are rejected with a
+     * &lt;not-acceptable/&gt; error.
+     * <p>
+     * Note that the registered {@link BytestreamListener} will NOT be notified on incoming Socks5
+     * bytestream requests sent in the context of <a
+     * href="http://xmpp.org/extensions/xep-0096.html">XEP-0096</a> file transfer. (See
+     * {@link FileTransferManager})
+     * 
+     * @param listener the listener to register
+     * @param initiatorJID the JID of the user that wants to establish a SOCKS5 Bytestream
+     */
+    public void addIncomingBytestreamListener(BytestreamListener listener, String initiatorJID) {
+        this.userListeners.put(initiatorJID, listener);
+    }
+
+    /**
+     * Removes the listener for the given user.
+     * 
+     * @param initiatorJID the JID of the user the listener should be removed
+     */
+    public void removeIncomingBytestreamListener(String initiatorJID) {
+        this.userListeners.remove(initiatorJID);
+    }
+
+    /**
+     * Use this method to ignore the next incoming SOCKS5 Bytestream request containing the given
+     * session ID. No listeners will be notified for this request and and no error will be returned
+     * to the initiator.
+     * <p>
+     * This method should be used if you are awaiting a SOCKS5 Bytestream request as a reply to
+     * another packet (e.g. file transfer).
+     * 
+     * @param sessionID to be ignored
+     */
+    public void ignoreBytestreamRequestOnce(String sessionID) {
+        this.ignoredBytestreamRequests.add(sessionID);
+    }
+
+    /**
+     * Disables the SOCKS5 Bytestream manager by removing the SOCKS5 Bytestream feature from the
+     * service discovery, disabling the listener for SOCKS5 Bytestream initiation requests and
+     * resetting its internal state.
+     * <p>
+     * To re-enable the SOCKS5 Bytestream feature invoke {@link #getBytestreamManager(Connection)}.
+     * Using the file transfer API will automatically re-enable the SOCKS5 Bytestream feature.
+     */
+    public synchronized void disableService() {
+
+        // remove initiation packet listener
+        this.connection.removePacketListener(this.initiationListener);
+
+        // shutdown threads
+        this.initiationListener.shutdown();
+
+        // clear listeners
+        this.allRequestListeners.clear();
+        this.userListeners.clear();
+
+        // reset internal state
+        this.lastWorkingProxy = null;
+        this.proxyBlacklist.clear();
+        this.ignoredBytestreamRequests.clear();
+
+        // remove manager from static managers map
+        managers.remove(this.connection);
+
+        // shutdown local SOCKS5 proxy if there are no more managers for other connections
+        if (managers.size() == 0) {
+            Socks5Proxy.getSocks5Proxy().stop();
+        }
+
+        // remove feature from service discovery
+        ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager.getInstanceFor(this.connection);
+
+        // check if service discovery is not already disposed by connection shutdown
+        if (serviceDiscoveryManager != null) {
+            serviceDiscoveryManager.removeFeature(NAMESPACE);
+        }
+
+    }
+
+    /**
+     * Returns the timeout to wait for the response to the SOCKS5 Bytestream initialization request.
+     * Default is 10000ms.
+     * 
+     * @return the timeout to wait for the response to the SOCKS5 Bytestream initialization request
+     */
+    public int getTargetResponseTimeout() {
+        if (this.targetResponseTimeout <= 0) {
+            this.targetResponseTimeout = 10000;
+        }
+        return targetResponseTimeout;
+    }
+
+    /**
+     * Sets the timeout to wait for the response to the SOCKS5 Bytestream initialization request.
+     * Default is 10000ms.
+     * 
+     * @param targetResponseTimeout the timeout to set
+     */
+    public void setTargetResponseTimeout(int targetResponseTimeout) {
+        this.targetResponseTimeout = targetResponseTimeout;
+    }
+
+    /**
+     * Returns the timeout for connecting to the SOCKS5 proxy selected by the target. Default is
+     * 10000ms.
+     * 
+     * @return the timeout for connecting to the SOCKS5 proxy selected by the target
+     */
+    public int getProxyConnectionTimeout() {
+        if (this.proxyConnectionTimeout <= 0) {
+            this.proxyConnectionTimeout = 10000;
+        }
+        return proxyConnectionTimeout;
+    }
+
+    /**
+     * Sets the timeout for connecting to the SOCKS5 proxy selected by the target. Default is
+     * 10000ms.
+     * 
+     * @param proxyConnectionTimeout the timeout to set
+     */
+    public void setProxyConnectionTimeout(int proxyConnectionTimeout) {
+        this.proxyConnectionTimeout = proxyConnectionTimeout;
+    }
+
+    /**
+     * Returns if the prioritization of the last working SOCKS5 proxy on successive SOCKS5
+     * Bytestream connections is enabled. Default is <code>true</code>.
+     * 
+     * @return <code>true</code> if prioritization is enabled, <code>false</code> otherwise
+     */
+    public boolean isProxyPrioritizationEnabled() {
+        return proxyPrioritizationEnabled;
+    }
+
+    /**
+     * Enable/disable the prioritization of the last working SOCKS5 proxy on successive SOCKS5
+     * Bytestream connections.
+     * 
+     * @param proxyPrioritizationEnabled enable/disable the prioritization of the last working
+     *        SOCKS5 proxy
+     */
+    public void setProxyPrioritizationEnabled(boolean proxyPrioritizationEnabled) {
+        this.proxyPrioritizationEnabled = proxyPrioritizationEnabled;
+    }
+
+    /**
+     * Establishes a SOCKS5 Bytestream with the given user and returns the Socket to send/receive
+     * data to/from the user.
+     * <p>
+     * Use this method to establish SOCKS5 Bytestreams to users accepting all incoming Socks5
+     * bytestream requests since this method doesn't provide a way to tell the user something about
+     * the data to be sent.
+     * <p>
+     * To establish a SOCKS5 Bytestream after negotiation the kind of data to be sent (e.g. file
+     * transfer) use {@link #establishSession(String, String)}.
+     * 
+     * @param targetJID the JID of the user a SOCKS5 Bytestream should be established
+     * @return the Socket to send/receive data to/from the user
+     * @throws XMPPException if the user doesn't support or accept SOCKS5 Bytestreams, if no Socks5
+     *         Proxy could be found, if the user couldn't connect to any of the SOCKS5 Proxies
+     * @throws IOException if the bytestream could not be established
+     * @throws InterruptedException if the current thread was interrupted while waiting
+     */
+    public Socks5BytestreamSession establishSession(String targetJID) throws XMPPException,
+                    IOException, InterruptedException {
+        String sessionID = getNextSessionID();
+        return establishSession(targetJID, sessionID);
+    }
+
+    /**
+     * Establishes a SOCKS5 Bytestream with the given user using the given session ID and returns
+     * the Socket to send/receive data to/from the user.
+     * 
+     * @param targetJID the JID of the user a SOCKS5 Bytestream should be established
+     * @param sessionID the session ID for the SOCKS5 Bytestream request
+     * @return the Socket to send/receive data to/from the user
+     * @throws XMPPException if the user doesn't support or accept SOCKS5 Bytestreams, if no Socks5
+     *         Proxy could be found, if the user couldn't connect to any of the SOCKS5 Proxies
+     * @throws IOException if the bytestream could not be established
+     * @throws InterruptedException if the current thread was interrupted while waiting
+     */
+    public Socks5BytestreamSession establishSession(String targetJID, String sessionID)
+                    throws XMPPException, IOException, InterruptedException {
+
+        XMPPException discoveryException = null;
+        // check if target supports SOCKS5 Bytestream
+        if (!supportsSocks5(targetJID)) {
+            throw new XMPPException(targetJID + " doesn't support SOCKS5 Bytestream");
+        }
+
+        List<String> proxies = new ArrayList<String>();
+        // determine SOCKS5 proxies from XMPP-server
+        try {
+            proxies.addAll(determineProxies());
+        } catch (XMPPException e) {
+            // don't abort here, just remember the exception thrown by determineProxies()
+            // determineStreamHostInfos() will at least add the local Socks5 proxy (if enabled)
+            discoveryException = e;
+        }
+
+        // determine address and port of each proxy
+        List<StreamHost> streamHosts = determineStreamHostInfos(proxies);
+
+        if (streamHosts.isEmpty()) {
+            throw discoveryException != null ? discoveryException : new XMPPException("no SOCKS5 proxies available");
+        }
+
+        // compute digest
+        String digest = Socks5Utils.createDigest(sessionID, this.connection.getUser(), targetJID);
+
+        // prioritize last working SOCKS5 proxy if exists
+        if (this.proxyPrioritizationEnabled && this.lastWorkingProxy != null) {
+            StreamHost selectedStreamHost = null;
+            for (StreamHost streamHost : streamHosts) {
+                if (streamHost.getJID().equals(this.lastWorkingProxy)) {
+                    selectedStreamHost = streamHost;
+                    break;
+                }
+            }
+            if (selectedStreamHost != null) {
+                streamHosts.remove(selectedStreamHost);
+                streamHosts.add(0, selectedStreamHost);
+            }
+
+        }
+
+        Socks5Proxy socks5Proxy = Socks5Proxy.getSocks5Proxy();
+        try {
+
+            // add transfer digest to local proxy to make transfer valid
+            socks5Proxy.addTransfer(digest);
+
+            // create initiation packet
+            Bytestream initiation = createBytestreamInitiation(sessionID, targetJID, streamHosts);
+
+            // send initiation packet
+            Packet response = SyncPacketSend.getReply(this.connection, initiation,
+                            getTargetResponseTimeout());
+
+            // extract used stream host from response
+            StreamHostUsed streamHostUsed = ((Bytestream) response).getUsedHost();
+            StreamHost usedStreamHost = initiation.getStreamHost(streamHostUsed.getJID());
+
+            if (usedStreamHost == null) {
+                throw new XMPPException("Remote user responded with unknown host");
+            }
+
+            // build SOCKS5 client
+            Socks5Client socks5Client = new Socks5ClientForInitiator(usedStreamHost, digest,
+                            this.connection, sessionID, targetJID);
+
+            // establish connection to proxy
+            Socket socket = socks5Client.getSocket(getProxyConnectionTimeout());
+
+            // remember last working SOCKS5 proxy to prioritize it for next request
+            this.lastWorkingProxy = usedStreamHost.getJID();
+
+            // negotiation successful, return the output stream
+            return new Socks5BytestreamSession(socket, usedStreamHost.getJID().equals(
+                            this.connection.getUser()));
+
+        }
+        catch (TimeoutException e) {
+            throw new IOException("Timeout while connecting to SOCKS5 proxy");
+        }
+        finally {
+
+            // remove transfer digest if output stream is returned or an exception
+            // occurred
+            socks5Proxy.removeTransfer(digest);
+
+        }
+    }
+
+    /**
+     * Returns <code>true</code> if the given target JID supports feature SOCKS5 Bytestream.
+     * 
+     * @param targetJID the target JID
+     * @return <code>true</code> if the given target JID supports feature SOCKS5 Bytestream
+     *         otherwise <code>false</code>
+     * @throws XMPPException if there was an error querying target for supported features
+     */
+    private boolean supportsSocks5(String targetJID) throws XMPPException {
+        ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager.getInstanceFor(this.connection);
+        DiscoverInfo discoverInfo = serviceDiscoveryManager.discoverInfo(targetJID);
+        return discoverInfo.containsFeature(NAMESPACE);
+    }
+
+    /**
+     * Returns a list of JIDs of SOCKS5 proxies by querying the XMPP server. The SOCKS5 proxies are
+     * in the same order as returned by the XMPP server.
+     * 
+     * @return list of JIDs of SOCKS5 proxies
+     * @throws XMPPException if there was an error querying the XMPP server for SOCKS5 proxies
+     */
+    private List<String> determineProxies() throws XMPPException {
+        ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager.getInstanceFor(this.connection);
+
+        List<String> proxies = new ArrayList<String>();
+
+        // get all items form XMPP server
+        DiscoverItems discoverItems = serviceDiscoveryManager.discoverItems(this.connection.getServiceName());
+        Iterator<Item> itemIterator = discoverItems.getItems();
+
+        // query all items if they are SOCKS5 proxies
+        while (itemIterator.hasNext()) {
+            Item item = itemIterator.next();
+
+            // skip blacklisted servers
+            if (this.proxyBlacklist.contains(item.getEntityID())) {
+                continue;
+            }
+
+            try {
+                DiscoverInfo proxyInfo;
+                proxyInfo = serviceDiscoveryManager.discoverInfo(item.getEntityID());
+                Iterator<Identity> identities = proxyInfo.getIdentities();
+
+                // item must have category "proxy" and type "bytestream"
+                while (identities.hasNext()) {
+                    Identity identity = identities.next();
+
+                    if ("proxy".equalsIgnoreCase(identity.getCategory())
+                                    && "bytestreams".equalsIgnoreCase(identity.getType())) {
+                        proxies.add(item.getEntityID());
+                        break;
+                    }
+
+                    /*
+                     * server is not a SOCKS5 proxy, blacklist server to skip next time a Socks5
+                     * bytestream should be established
+                     */
+                    this.proxyBlacklist.add(item.getEntityID());
+
+                }
+            }
+            catch (XMPPException e) {
+                // blacklist errornous server
+                this.proxyBlacklist.add(item.getEntityID());
+            }
+        }
+
+        return proxies;
+    }
+
+    /**
+     * Returns a list of stream hosts containing the IP address an the port for the given list of
+     * SOCKS5 proxy JIDs. The order of the returned list is the same as the given list of JIDs
+     * excluding all SOCKS5 proxies who's network settings could not be determined. If a local
+     * SOCKS5 proxy is running it will be the first item in the list returned.
+     * 
+     * @param proxies a list of SOCKS5 proxy JIDs
+     * @return a list of stream hosts containing the IP address an the port
+     */
+    private List<StreamHost> determineStreamHostInfos(List<String> proxies) {
+        List<StreamHost> streamHosts = new ArrayList<StreamHost>();
+
+        // add local proxy on first position if exists
+        List<StreamHost> localProxies = getLocalStreamHost();
+        if (localProxies != null) {
+            streamHosts.addAll(localProxies);
+        }
+
+        // query SOCKS5 proxies for network settings
+        for (String proxy : proxies) {
+            Bytestream streamHostRequest = createStreamHostRequest(proxy);
+            try {
+                Bytestream response = (Bytestream) SyncPacketSend.getReply(this.connection,
+                                streamHostRequest);
+                streamHosts.addAll(response.getStreamHosts());
+            }
+            catch (XMPPException e) {
+                // blacklist errornous proxies
+                this.proxyBlacklist.add(proxy);
+            }
+        }
+
+        return streamHosts;
+    }
+
+    /**
+     * Returns a IQ packet to query a SOCKS5 proxy its network settings.
+     * 
+     * @param proxy the proxy to query
+     * @return IQ packet to query a SOCKS5 proxy its network settings
+     */
+    private Bytestream createStreamHostRequest(String proxy) {
+        Bytestream request = new Bytestream();
+        request.setType(IQ.Type.GET);
+        request.setTo(proxy);
+        return request;
+    }
+
+    /**
+     * Returns the stream host information of the local SOCKS5 proxy containing the IP address and
+     * the port or null if local SOCKS5 proxy is not running.
+     * 
+     * @return the stream host information of the local SOCKS5 proxy or null if local SOCKS5 proxy
+     *         is not running
+     */
+    private List<StreamHost> getLocalStreamHost() {
+
+        // get local proxy singleton
+        Socks5Proxy socks5Server = Socks5Proxy.getSocks5Proxy();
+
+        if (socks5Server.isRunning()) {
+            List<String> addresses = socks5Server.getLocalAddresses();
+            int port = socks5Server.getPort();
+
+            if (addresses.size() >= 1) {
+                List<StreamHost> streamHosts = new ArrayList<StreamHost>();
+                for (String address : addresses) {
+                    StreamHost streamHost = new StreamHost(this.connection.getUser(), address);
+                    streamHost.setPort(port);
+                    streamHosts.add(streamHost);
+                }
+                return streamHosts;
+            }
+
+        }
+
+        // server is not running or local address could not be determined
+        return null;
+    }
+
+    /**
+     * Returns a SOCKS5 Bytestream initialization request packet with the given session ID
+     * containing the given stream hosts for the given target JID.
+     * 
+     * @param sessionID the session ID for the SOCKS5 Bytestream
+     * @param targetJID the target JID of SOCKS5 Bytestream request
+     * @param streamHosts a list of SOCKS5 proxies the target should connect to
+     * @return a SOCKS5 Bytestream initialization request packet
+     */
+    private Bytestream createBytestreamInitiation(String sessionID, String targetJID,
+                    List<StreamHost> streamHosts) {
+        Bytestream initiation = new Bytestream(sessionID);
+
+        // add all stream hosts
+        for (StreamHost streamHost : streamHosts) {
+            initiation.addStreamHost(streamHost);
+        }
+
+        initiation.setType(IQ.Type.SET);
+        initiation.setTo(targetJID);
+
+        return initiation;
+    }
+
+    /**
+     * Responses to the given packet's sender with a XMPP error that a SOCKS5 Bytestream is not
+     * accepted.
+     * 
+     * @param packet Packet that should be answered with a not-acceptable error
+     */
+    protected void replyRejectPacket(IQ packet) {
+        XMPPError xmppError = new XMPPError(XMPPError.Condition.no_acceptable);
+        IQ errorIQ = IQ.createErrorResponse(packet, xmppError);
+        this.connection.sendPacket(errorIQ);
+    }
+
+    /**
+     * Activates the Socks5BytestreamManager by registering the SOCKS5 Bytestream initialization
+     * listener and enabling the SOCKS5 Bytestream feature.
+     */
+    private void activate() {
+        // register bytestream initiation packet listener
+        this.connection.addPacketListener(this.initiationListener,
+                        this.initiationListener.getFilter());
+
+        // enable SOCKS5 feature
+        enableService();
+    }
+
+    /**
+     * Adds the SOCKS5 Bytestream feature to the service discovery.
+     */
+    private void enableService() {
+        ServiceDiscoveryManager manager = ServiceDiscoveryManager.getInstanceFor(this.connection);
+        if (!manager.includesFeature(NAMESPACE)) {
+            manager.addFeature(NAMESPACE);
+        }
+    }
+
+    /**
+     * Returns a new unique session ID.
+     * 
+     * @return a new unique session ID
+     */
+    private String getNextSessionID() {
+        StringBuilder buffer = new StringBuilder();
+        buffer.append(SESSION_ID_PREFIX);
+        buffer.append(Math.abs(randomGenerator.nextLong()));
+        return buffer.toString();
+    }
+
+    /**
+     * Returns the XMPP connection.
+     * 
+     * @return the XMPP connection
+     */
+    protected Connection getConnection() {
+        return this.connection;
+    }
+
+    /**
+     * Returns the {@link BytestreamListener} that should be informed if a SOCKS5 Bytestream request
+     * from the given initiator JID is received.
+     * 
+     * @param initiator the initiator's JID
+     * @return the listener
+     */
+    protected BytestreamListener getUserListener(String initiator) {
+        return this.userListeners.get(initiator);
+    }
+
+    /**
+     * Returns a list of {@link BytestreamListener} that are informed if there are no listeners for
+     * a specific initiator.
+     * 
+     * @return list of listeners
+     */
+    protected List<BytestreamListener> getAllRequestListeners() {
+        return this.allRequestListeners;
+    }
+
+    /**
+     * Returns the list of session IDs that should be ignored by the InitialtionListener
+     * 
+     * @return list of session IDs
+     */
+    protected List<String> getIgnoredBytestreamRequests() {
+        return ignoredBytestreamRequests;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java
new file mode 100644
index 0000000..0b2fdeb
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamRequest.java
@@ -0,0 +1,316 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.IOException;
+import java.net.Socket;
+import java.util.Collection;
+import java.util.concurrent.TimeoutException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.Cache;
+import org.jivesoftware.smackx.bytestreams.BytestreamRequest;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost;
+
+/**
+ * Socks5BytestreamRequest class handles incoming SOCKS5 Bytestream requests.
+ * 
+ * @author Henning Staib
+ */
+public class Socks5BytestreamRequest implements BytestreamRequest {
+
+    /* lifetime of an Item in the blacklist */
+    private static final long BLACKLIST_LIFETIME = 60 * 1000 * 120;
+
+    /* size of the blacklist */
+    private static final int BLACKLIST_MAX_SIZE = 100;
+
+    /* blacklist of addresses of SOCKS5 proxies */
+    private static final Cache<String, Integer> ADDRESS_BLACKLIST = new Cache<String, Integer>(
+                    BLACKLIST_MAX_SIZE, BLACKLIST_LIFETIME);
+
+    /*
+     * The number of connection failures it takes for a particular SOCKS5 proxy to be blacklisted.
+     * When a proxy is blacklisted no more connection attempts will be made to it for a period of 2
+     * hours.
+     */
+    private static int CONNECTION_FAILURE_THRESHOLD = 2;
+
+    /* the bytestream initialization request */
+    private Bytestream bytestreamRequest;
+
+    /* SOCKS5 Bytestream manager containing the XMPP connection and helper methods */
+    private Socks5BytestreamManager manager;
+
+    /* timeout to connect to all SOCKS5 proxies */
+    private int totalConnectTimeout = 10000;
+
+    /* minimum timeout to connect to one SOCKS5 proxy */
+    private int minimumConnectTimeout = 2000;
+
+    /**
+     * Returns the number of connection failures it takes for a particular SOCKS5 proxy to be
+     * blacklisted. When a proxy is blacklisted no more connection attempts will be made to it for a
+     * period of 2 hours. Default is 2.
+     * 
+     * @return the number of connection failures it takes for a particular SOCKS5 proxy to be
+     *         blacklisted
+     */
+    public static int getConnectFailureThreshold() {
+        return CONNECTION_FAILURE_THRESHOLD;
+    }
+
+    /**
+     * Sets the number of connection failures it takes for a particular SOCKS5 proxy to be
+     * blacklisted. When a proxy is blacklisted no more connection attempts will be made to it for a
+     * period of 2 hours. Default is 2.
+     * <p>
+     * Setting the connection failure threshold to zero disables the blacklisting.
+     * 
+     * @param connectFailureThreshold the number of connection failures it takes for a particular
+     *        SOCKS5 proxy to be blacklisted
+     */
+    public static void setConnectFailureThreshold(int connectFailureThreshold) {
+        CONNECTION_FAILURE_THRESHOLD = connectFailureThreshold;
+    }
+
+    /**
+     * Creates a new Socks5BytestreamRequest.
+     * 
+     * @param manager the SOCKS5 Bytestream manager
+     * @param bytestreamRequest the SOCKS5 Bytestream initialization packet
+     */
+    protected Socks5BytestreamRequest(Socks5BytestreamManager manager, Bytestream bytestreamRequest) {
+        this.manager = manager;
+        this.bytestreamRequest = bytestreamRequest;
+    }
+
+    /**
+     * Returns the maximum timeout to connect to SOCKS5 proxies. Default is 10000ms.
+     * <p>
+     * When accepting a SOCKS5 Bytestream request Smack tries to connect to all SOCKS5 proxies given
+     * by the initiator until a connection is established. This timeout divided by the number of
+     * SOCKS5 proxies determines the timeout for every connection attempt.
+     * <p>
+     * You can set the minimum timeout for establishing a connection to one SOCKS5 proxy by invoking
+     * {@link #setMinimumConnectTimeout(int)}.
+     * 
+     * @return the maximum timeout to connect to SOCKS5 proxies
+     */
+    public int getTotalConnectTimeout() {
+        if (this.totalConnectTimeout <= 0) {
+            return 10000;
+        }
+        return this.totalConnectTimeout;
+    }
+
+    /**
+     * Sets the maximum timeout to connect to SOCKS5 proxies. Default is 10000ms.
+     * <p>
+     * When accepting a SOCKS5 Bytestream request Smack tries to connect to all SOCKS5 proxies given
+     * by the initiator until a connection is established. This timeout divided by the number of
+     * SOCKS5 proxies determines the timeout for every connection attempt.
+     * <p>
+     * You can set the minimum timeout for establishing a connection to one SOCKS5 proxy by invoking
+     * {@link #setMinimumConnectTimeout(int)}.
+     * 
+     * @param totalConnectTimeout the maximum timeout to connect to SOCKS5 proxies
+     */
+    public void setTotalConnectTimeout(int totalConnectTimeout) {
+        this.totalConnectTimeout = totalConnectTimeout;
+    }
+
+    /**
+     * Returns the timeout to connect to one SOCKS5 proxy while accepting the SOCKS5 Bytestream
+     * request. Default is 2000ms.
+     * 
+     * @return the timeout to connect to one SOCKS5 proxy
+     */
+    public int getMinimumConnectTimeout() {
+        if (this.minimumConnectTimeout <= 0) {
+            return 2000;
+        }
+        return this.minimumConnectTimeout;
+    }
+
+    /**
+     * Sets the timeout to connect to one SOCKS5 proxy while accepting the SOCKS5 Bytestream
+     * request. Default is 2000ms.
+     * 
+     * @param minimumConnectTimeout the timeout to connect to one SOCKS5 proxy
+     */
+    public void setMinimumConnectTimeout(int minimumConnectTimeout) {
+        this.minimumConnectTimeout = minimumConnectTimeout;
+    }
+
+    /**
+     * Returns the sender of the SOCKS5 Bytestream initialization request.
+     * 
+     * @return the sender of the SOCKS5 Bytestream initialization request.
+     */
+    public String getFrom() {
+        return this.bytestreamRequest.getFrom();
+    }
+
+    /**
+     * Returns the session ID of the SOCKS5 Bytestream initialization request.
+     * 
+     * @return the session ID of the SOCKS5 Bytestream initialization request.
+     */
+    public String getSessionID() {
+        return this.bytestreamRequest.getSessionID();
+    }
+
+    /**
+     * Accepts the SOCKS5 Bytestream initialization request and returns the socket to send/receive
+     * data.
+     * <p>
+     * Before accepting the SOCKS5 Bytestream request you can set timeouts by invoking
+     * {@link #setTotalConnectTimeout(int)} and {@link #setMinimumConnectTimeout(int)}.
+     * 
+     * @return the socket to send/receive data
+     * @throws XMPPException if connection to all SOCKS5 proxies failed or if stream is invalid.
+     * @throws InterruptedException if the current thread was interrupted while waiting
+     */
+    public Socks5BytestreamSession accept() throws XMPPException, InterruptedException {
+        Collection<StreamHost> streamHosts = this.bytestreamRequest.getStreamHosts();
+
+        // throw exceptions if request contains no stream hosts
+        if (streamHosts.size() == 0) {
+            cancelRequest();
+        }
+
+        StreamHost selectedHost = null;
+        Socket socket = null;
+
+        String digest = Socks5Utils.createDigest(this.bytestreamRequest.getSessionID(),
+                        this.bytestreamRequest.getFrom(), this.manager.getConnection().getUser());
+
+        /*
+         * determine timeout for each connection attempt; each SOCKS5 proxy has the same amount of
+         * time so that the first does not consume the whole timeout
+         */
+        int timeout = Math.max(getTotalConnectTimeout() / streamHosts.size(),
+                        getMinimumConnectTimeout());
+
+        for (StreamHost streamHost : streamHosts) {
+            String address = streamHost.getAddress() + ":" + streamHost.getPort();
+
+            // check to see if this address has been blacklisted
+            int failures = getConnectionFailures(address);
+            if (CONNECTION_FAILURE_THRESHOLD > 0 && failures >= CONNECTION_FAILURE_THRESHOLD) {
+                continue;
+            }
+
+            // establish socket
+            try {
+
+                // build SOCKS5 client
+                final Socks5Client socks5Client = new Socks5Client(streamHost, digest);
+
+                // connect to SOCKS5 proxy with a timeout
+                socket = socks5Client.getSocket(timeout);
+
+                // set selected host
+                selectedHost = streamHost;
+                break;
+
+            }
+            catch (TimeoutException e) {
+                incrementConnectionFailures(address);
+            }
+            catch (IOException e) {
+                incrementConnectionFailures(address);
+            }
+            catch (XMPPException e) {
+                incrementConnectionFailures(address);
+            }
+
+        }
+
+        // throw exception if connecting to all SOCKS5 proxies failed
+        if (selectedHost == null || socket == null) {
+            cancelRequest();
+        }
+
+        // send used-host confirmation
+        Bytestream response = createUsedHostResponse(selectedHost);
+        this.manager.getConnection().sendPacket(response);
+
+        return new Socks5BytestreamSession(socket, selectedHost.getJID().equals(
+                        this.bytestreamRequest.getFrom()));
+
+    }
+
+    /**
+     * Rejects the SOCKS5 Bytestream request by sending a reject error to the initiator.
+     */
+    public void reject() {
+        this.manager.replyRejectPacket(this.bytestreamRequest);
+    }
+
+    /**
+     * Cancels the SOCKS5 Bytestream request by sending an error to the initiator and building a
+     * XMPP exception.
+     * 
+     * @throws XMPPException XMPP exception containing the XMPP error
+     */
+    private void cancelRequest() throws XMPPException {
+        String errorMessage = "Could not establish socket with any provided host";
+        XMPPError error = new XMPPError(XMPPError.Condition.item_not_found, errorMessage);
+        IQ errorIQ = IQ.createErrorResponse(this.bytestreamRequest, error);
+        this.manager.getConnection().sendPacket(errorIQ);
+        throw new XMPPException(errorMessage, error);
+    }
+
+    /**
+     * Returns the response to the SOCKS5 Bytestream request containing the SOCKS5 proxy used.
+     * 
+     * @param selectedHost the used SOCKS5 proxy
+     * @return the response to the SOCKS5 Bytestream request
+     */
+    private Bytestream createUsedHostResponse(StreamHost selectedHost) {
+        Bytestream response = new Bytestream(this.bytestreamRequest.getSessionID());
+        response.setTo(this.bytestreamRequest.getFrom());
+        response.setType(IQ.Type.RESULT);
+        response.setPacketID(this.bytestreamRequest.getPacketID());
+        response.setUsedHost(selectedHost.getJID());
+        return response;
+    }
+
+    /**
+     * Increments the connection failure counter by one for the given address.
+     * 
+     * @param address the address the connection failure counter should be increased
+     */
+    private void incrementConnectionFailures(String address) {
+        Integer count = ADDRESS_BLACKLIST.get(address);
+        ADDRESS_BLACKLIST.put(address, count == null ? 1 : count + 1);
+    }
+
+    /**
+     * Returns how often the connection to the given address failed.
+     * 
+     * @param address the address
+     * @return number of connection failures
+     */
+    private int getConnectionFailures(String address) {
+        Integer count = ADDRESS_BLACKLIST.get(address);
+        return count != null ? count : 0;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamSession.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamSession.java
new file mode 100644
index 0000000..41ab142
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5BytestreamSession.java
@@ -0,0 +1,98 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.Socket;
+import java.net.SocketException;
+
+import org.jivesoftware.smackx.bytestreams.BytestreamSession;
+
+/**
+ * Socks5BytestreamSession class represents a SOCKS5 Bytestream session.
+ * 
+ * @author Henning Staib
+ */
+public class Socks5BytestreamSession implements BytestreamSession {
+
+    /* the underlying socket of the SOCKS5 Bytestream */
+    private final Socket socket;
+
+    /* flag to indicate if this session is a direct or mediated connection */
+    private final boolean isDirect;
+
+    protected Socks5BytestreamSession(Socket socket, boolean isDirect) {
+        this.socket = socket;
+        this.isDirect = isDirect;
+    }
+
+    /**
+     * Returns <code>true</code> if the session is established through a direct connection between
+     * the initiator and target, <code>false</code> if the session is mediated over a SOCKS proxy.
+     * 
+     * @return <code>true</code> if session is a direct connection, <code>false</code> if session is
+     *         mediated over a SOCKS5 proxy
+     */
+    public boolean isDirect() {
+        return this.isDirect;
+    }
+
+    /**
+     * Returns <code>true</code> if the session is mediated over a SOCKS proxy, <code>false</code>
+     * if this session is established through a direct connection between the initiator and target.
+     * 
+     * @return <code>true</code> if session is mediated over a SOCKS5 proxy, <code>false</code> if
+     *         session is a direct connection
+     */
+    public boolean isMediated() {
+        return !this.isDirect;
+    }
+
+    public InputStream getInputStream() throws IOException {
+        return this.socket.getInputStream();
+    }
+
+    public OutputStream getOutputStream() throws IOException {
+        return this.socket.getOutputStream();
+    }
+
+    public int getReadTimeout() throws IOException {
+        try {
+            return this.socket.getSoTimeout();
+        }
+        catch (SocketException e) {
+            throw new IOException("Error on underlying Socket");
+        }
+    }
+
+    public void setReadTimeout(int timeout) throws IOException {
+        try {
+            this.socket.setSoTimeout(timeout);
+        }
+        catch (SocketException e) {
+            throw new IOException("Error on underlying Socket");
+        }
+    }
+
+    public void close() throws IOException {
+        this.socket.close();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java
new file mode 100644
index 0000000..664ea59
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Client.java
@@ -0,0 +1,204 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.DataInputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.net.InetSocketAddress;
+import java.net.Socket;
+import java.net.SocketAddress;
+import java.util.Arrays;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.FutureTask;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.TimeoutException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost;
+
+/**
+ * The SOCKS5 client class handles establishing a connection to a SOCKS5 proxy. Connecting to a
+ * SOCKS5 proxy requires authentication. This implementation only supports the no-authentication
+ * authentication method.
+ * 
+ * @author Henning Staib
+ */
+class Socks5Client {
+
+    /* stream host containing network settings and name of the SOCKS5 proxy */
+    protected StreamHost streamHost;
+
+    /* SHA-1 digest identifying the SOCKS5 stream */
+    protected String digest;
+
+    /**
+     * Constructor for a SOCKS5 client.
+     * 
+     * @param streamHost containing network settings of the SOCKS5 proxy
+     * @param digest identifying the SOCKS5 Bytestream
+     */
+    public Socks5Client(StreamHost streamHost, String digest) {
+        this.streamHost = streamHost;
+        this.digest = digest;
+    }
+
+    /**
+     * Returns the initialized socket that can be used to transfer data between peers via the SOCKS5
+     * proxy.
+     * 
+     * @param timeout timeout to connect to SOCKS5 proxy in milliseconds
+     * @return socket the initialized socket
+     * @throws IOException if initializing the socket failed due to a network error
+     * @throws XMPPException if establishing connection to SOCKS5 proxy failed
+     * @throws TimeoutException if connecting to SOCKS5 proxy timed out
+     * @throws InterruptedException if the current thread was interrupted while waiting
+     */
+    public Socket getSocket(int timeout) throws IOException, XMPPException, InterruptedException,
+                    TimeoutException {
+
+        // wrap connecting in future for timeout
+        FutureTask<Socket> futureTask = new FutureTask<Socket>(new Callable<Socket>() {
+
+            public Socket call() throws Exception {
+
+                // initialize socket
+                Socket socket = new Socket();
+                SocketAddress socketAddress = new InetSocketAddress(streamHost.getAddress(),
+                                streamHost.getPort());
+                socket.connect(socketAddress);
+
+                // initialize connection to SOCKS5 proxy
+                if (!establish(socket)) {
+
+                    // initialization failed, close socket
+                    socket.close();
+                    throw new XMPPException("establishing connection to SOCKS5 proxy failed");
+
+                }
+
+                return socket;
+            }
+
+        });
+        Thread executor = new Thread(futureTask);
+        executor.start();
+
+        // get connection to initiator with timeout
+        try {
+            return futureTask.get(timeout, TimeUnit.MILLISECONDS);
+        }
+        catch (ExecutionException e) {
+            Throwable cause = e.getCause();
+            if (cause != null) {
+                // case exceptions to comply with method signature
+                if (cause instanceof IOException) {
+                    throw (IOException) cause;
+                }
+                if (cause instanceof XMPPException) {
+                    throw (XMPPException) cause;
+                }
+            }
+
+            // throw generic IO exception if unexpected exception was thrown
+            throw new IOException("Error while connection to SOCKS5 proxy");
+        }
+
+    }
+
+    /**
+     * Initializes the connection to the SOCKS5 proxy by negotiating authentication method and
+     * requesting a stream for the given digest. Currently only the no-authentication method is
+     * supported by the Socks5Client.
+     * <p>
+     * Returns <code>true</code> if a stream could be established, otherwise <code>false</code>. If
+     * <code>false</code> is returned the given Socket should be closed.
+     * 
+     * @param socket connected to a SOCKS5 proxy
+     * @return <code>true</code> if if a stream could be established, otherwise <code>false</code>.
+     *         If <code>false</code> is returned the given Socket should be closed.
+     * @throws IOException if a network error occurred
+     */
+    protected boolean establish(Socket socket) throws IOException {
+
+        /*
+         * use DataInputStream/DataOutpuStream to assure read and write is completed in a single
+         * statement
+         */
+        DataInputStream in = new DataInputStream(socket.getInputStream());
+        DataOutputStream out = new DataOutputStream(socket.getOutputStream());
+
+        // authentication negotiation
+        byte[] cmd = new byte[3];
+
+        cmd[0] = (byte) 0x05; // protocol version 5
+        cmd[1] = (byte) 0x01; // number of authentication methods supported
+        cmd[2] = (byte) 0x00; // authentication method: no-authentication required
+
+        out.write(cmd);
+        out.flush();
+
+        byte[] response = new byte[2];
+        in.readFully(response);
+
+        // check if server responded with correct version and no-authentication method
+        if (response[0] != (byte) 0x05 || response[1] != (byte) 0x00) {
+            return false;
+        }
+
+        // request SOCKS5 connection with given address/digest
+        byte[] connectionRequest = createSocks5ConnectRequest();
+        out.write(connectionRequest);
+        out.flush();
+
+        // receive response
+        byte[] connectionResponse;
+        try {
+            connectionResponse = Socks5Utils.receiveSocks5Message(in);
+        }
+        catch (XMPPException e) {
+            return false; // server answered in an unsupported way
+        }
+
+        // verify response
+        connectionRequest[1] = (byte) 0x00; // set expected return status to 0
+        return Arrays.equals(connectionRequest, connectionResponse);
+    }
+
+    /**
+     * Returns a SOCKS5 connection request message. It contains the command "connect", the address
+     * type "domain" and the digest as address.
+     * <p>
+     * (see <a href="http://tools.ietf.org/html/rfc1928">RFC1928</a>)
+     * 
+     * @return SOCKS5 connection request message
+     */
+    private byte[] createSocks5ConnectRequest() {
+        byte addr[] = this.digest.getBytes();
+
+        byte[] data = new byte[7 + addr.length];
+        data[0] = (byte) 0x05; // version (SOCKS5)
+        data[1] = (byte) 0x01; // command (1 - connect)
+        data[2] = (byte) 0x00; // reserved byte (always 0)
+        data[3] = (byte) 0x03; // address type (3 - domain name)
+        data[4] = (byte) addr.length; // address length
+        System.arraycopy(addr, 0, data, 5, addr.length); // address
+        data[data.length - 2] = (byte) 0; // address port (2 bytes always 0)
+        data[data.length - 1] = (byte) 0;
+
+        return data;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java
new file mode 100644
index 0000000..0d90791
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5ClientForInitiator.java
@@ -0,0 +1,117 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.IOException;
+import java.net.Socket;
+import java.util.concurrent.TimeoutException;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.util.SyncPacketSend;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream.StreamHost;
+
+/**
+ * Implementation of a SOCKS5 client used on the initiators side. This is needed because connecting
+ * to the local SOCKS5 proxy differs form the regular way to connect to a SOCKS5 proxy. Additionally
+ * a remote SOCKS5 proxy has to be activated by the initiator before data can be transferred between
+ * the peers.
+ * 
+ * @author Henning Staib
+ */
+class Socks5ClientForInitiator extends Socks5Client {
+
+    /* the XMPP connection used to communicate with the SOCKS5 proxy */
+    private Connection connection;
+
+    /* the session ID used to activate SOCKS5 stream */
+    private String sessionID;
+
+    /* the target JID used to activate SOCKS5 stream */
+    private String target;
+
+    /**
+     * Creates a new SOCKS5 client for the initiators side.
+     * 
+     * @param streamHost containing network settings of the SOCKS5 proxy
+     * @param digest identifying the SOCKS5 Bytestream
+     * @param connection the XMPP connection
+     * @param sessionID the session ID of the SOCKS5 Bytestream
+     * @param target the target JID of the SOCKS5 Bytestream
+     */
+    public Socks5ClientForInitiator(StreamHost streamHost, String digest, Connection connection,
+                    String sessionID, String target) {
+        super(streamHost, digest);
+        this.connection = connection;
+        this.sessionID = sessionID;
+        this.target = target;
+    }
+
+    public Socket getSocket(int timeout) throws IOException, XMPPException, InterruptedException,
+                    TimeoutException {
+        Socket socket = null;
+
+        // check if stream host is the local SOCKS5 proxy
+        if (this.streamHost.getJID().equals(this.connection.getUser())) {
+            Socks5Proxy socks5Server = Socks5Proxy.getSocks5Proxy();
+            socket = socks5Server.getSocket(this.digest);
+            if (socket == null) {
+                throw new XMPPException("target is not connected to SOCKS5 proxy");
+            }
+        }
+        else {
+            socket = super.getSocket(timeout);
+
+            try {
+                activate();
+            }
+            catch (XMPPException e) {
+                socket.close();
+                throw new XMPPException("activating SOCKS5 Bytestream failed", e);
+            }
+
+        }
+
+        return socket;
+    }
+
+    /**
+     * Activates the SOCKS5 Bytestream by sending a XMPP SOCKS5 Bytestream activation packet to the
+     * SOCKS5 proxy.
+     */
+    private void activate() throws XMPPException {
+        Bytestream activate = createStreamHostActivation();
+        // if activation fails #getReply throws an exception
+        SyncPacketSend.getReply(this.connection, activate);
+    }
+
+    /**
+     * Returns a SOCKS5 Bytestream activation packet.
+     * 
+     * @return SOCKS5 Bytestream activation packet
+     */
+    private Bytestream createStreamHostActivation() {
+        Bytestream activate = new Bytestream(this.sessionID);
+        activate.setMode(null);
+        activate.setType(IQ.Type.SET);
+        activate.setTo(this.streamHost.getJID());
+
+        activate.setToActivate(this.target);
+
+        return activate;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java
new file mode 100644
index 0000000..11ef7a9
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Proxy.java
@@ -0,0 +1,423 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.DataInputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.net.InetAddress;
+import java.net.ServerSocket;
+import java.net.Socket;
+import java.net.SocketException;
+import java.net.UnknownHostException;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.LinkedHashSet;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+
+/**
+ * The Socks5Proxy class represents a local SOCKS5 proxy server. It can be enabled/disabled by
+ * setting the <code>localSocks5ProxyEnabled</code> flag in the <code>smack-config.xml</code> or by
+ * invoking {@link SmackConfiguration#setLocalSocks5ProxyEnabled(boolean)}. The proxy is enabled by
+ * default.
+ * <p>
+ * The port of the local SOCKS5 proxy can be configured by setting <code>localSocks5ProxyPort</code>
+ * in the <code>smack-config.xml</code> or by invoking
+ * {@link SmackConfiguration#setLocalSocks5ProxyPort(int)}. Default port is 7777. If you set the
+ * port to a negative value Smack tries to the absolute value and all following until it finds an
+ * open port.
+ * <p>
+ * If your application is running on a machine with multiple network interfaces or if you want to
+ * provide your public address in case you are behind a NAT router, invoke
+ * {@link #addLocalAddress(String)} or {@link #replaceLocalAddresses(List)} to modify the list of
+ * local network addresses used for outgoing SOCKS5 Bytestream requests.
+ * <p>
+ * The local SOCKS5 proxy server refuses all connections except the ones that are explicitly allowed
+ * in the process of establishing a SOCKS5 Bytestream (
+ * {@link Socks5BytestreamManager#establishSession(String)}).
+ * <p>
+ * This Implementation has the following limitations:
+ * <ul>
+ * <li>only supports the no-authentication authentication method</li>
+ * <li>only supports the <code>connect</code> command and will not answer correctly to other
+ * commands</li>
+ * <li>only supports requests with the domain address type and will not correctly answer to requests
+ * with other address types</li>
+ * </ul>
+ * (see <a href="http://tools.ietf.org/html/rfc1928">RFC 1928</a>)
+ * 
+ * @author Henning Staib
+ */
+public class Socks5Proxy {
+
+    /* SOCKS5 proxy singleton */
+    private static Socks5Proxy socks5Server;
+
+    /* reusable implementation of a SOCKS5 proxy server process */
+    private Socks5ServerProcess serverProcess;
+
+    /* thread running the SOCKS5 server process */
+    private Thread serverThread;
+
+    /* server socket to accept SOCKS5 connections */
+    private ServerSocket serverSocket;
+
+    /* assigns a connection to a digest */
+    private final Map<String, Socket> connectionMap = new ConcurrentHashMap<String, Socket>();
+
+    /* list of digests connections should be stored */
+    private final List<String> allowedConnections = Collections.synchronizedList(new LinkedList<String>());
+
+    private final Set<String> localAddresses = Collections.synchronizedSet(new LinkedHashSet<String>());
+
+    /**
+     * Private constructor.
+     */
+    private Socks5Proxy() {
+        this.serverProcess = new Socks5ServerProcess();
+
+        // add default local address
+        try {
+            this.localAddresses.add(InetAddress.getLocalHost().getHostAddress());
+        }
+        catch (UnknownHostException e) {
+            // do nothing
+        }
+
+    }
+
+    /**
+     * Returns the local SOCKS5 proxy server.
+     * 
+     * @return the local SOCKS5 proxy server
+     */
+    public static synchronized Socks5Proxy getSocks5Proxy() {
+        if (socks5Server == null) {
+            socks5Server = new Socks5Proxy();
+        }
+        if (SmackConfiguration.isLocalSocks5ProxyEnabled()) {
+            socks5Server.start();
+        }
+        return socks5Server;
+    }
+
+    /**
+     * Starts the local SOCKS5 proxy server. If it is already running, this method does nothing.
+     */
+    public synchronized void start() {
+        if (isRunning()) {
+            return;
+        }
+        try {
+            if (SmackConfiguration.getLocalSocks5ProxyPort() < 0) {
+                int port = Math.abs(SmackConfiguration.getLocalSocks5ProxyPort());
+                for (int i = 0; i < 65535 - port; i++) {
+                    try {
+                        this.serverSocket = new ServerSocket(port + i);
+                        break;
+                    }
+                    catch (IOException e) {
+                        // port is used, try next one
+                    }
+                }
+            }
+            else {
+                this.serverSocket = new ServerSocket(SmackConfiguration.getLocalSocks5ProxyPort());
+            }
+
+            if (this.serverSocket != null) {
+                this.serverThread = new Thread(this.serverProcess);
+                this.serverThread.start();
+            }
+        }
+        catch (IOException e) {
+            // couldn't setup server
+            System.err.println("couldn't setup local SOCKS5 proxy on port "
+                            + SmackConfiguration.getLocalSocks5ProxyPort() + ": " + e.getMessage());
+        }
+    }
+
+    /**
+     * Stops the local SOCKS5 proxy server. If it is not running this method does nothing.
+     */
+    public synchronized void stop() {
+        if (!isRunning()) {
+            return;
+        }
+
+        try {
+            this.serverSocket.close();
+        }
+        catch (IOException e) {
+            // do nothing
+        }
+
+        if (this.serverThread != null && this.serverThread.isAlive()) {
+            try {
+                this.serverThread.interrupt();
+                this.serverThread.join();
+            }
+            catch (InterruptedException e) {
+                // do nothing
+            }
+        }
+        this.serverThread = null;
+        this.serverSocket = null;
+
+    }
+
+    /**
+     * Adds the given address to the list of local network addresses.
+     * <p>
+     * Use this method if you want to provide multiple addresses in a SOCKS5 Bytestream request.
+     * This may be necessary if your application is running on a machine with multiple network
+     * interfaces or if you want to provide your public address in case you are behind a NAT router.
+     * <p>
+     * The order of the addresses used is determined by the order you add addresses.
+     * <p>
+     * Note that the list of addresses initially contains the address returned by
+     * <code>InetAddress.getLocalHost().getHostAddress()</code>. You can replace the list of
+     * addresses by invoking {@link #replaceLocalAddresses(List)}.
+     * 
+     * @param address the local network address to add
+     */
+    public void addLocalAddress(String address) {
+        if (address == null) {
+            throw new IllegalArgumentException("address may not be null");
+        }
+        this.localAddresses.add(address);
+    }
+
+    /**
+     * Removes the given address from the list of local network addresses. This address will then no
+     * longer be used of outgoing SOCKS5 Bytestream requests.
+     * 
+     * @param address the local network address to remove
+     */
+    public void removeLocalAddress(String address) {
+        this.localAddresses.remove(address);
+    }
+
+    /**
+     * Returns an unmodifiable list of the local network addresses that will be used for streamhost
+     * candidates of outgoing SOCKS5 Bytestream requests.
+     * 
+     * @return unmodifiable list of the local network addresses
+     */
+    public List<String> getLocalAddresses() {
+        return Collections.unmodifiableList(new ArrayList<String>(this.localAddresses));
+    }
+
+    /**
+     * Replaces the list of local network addresses.
+     * <p>
+     * Use this method if you want to provide multiple addresses in a SOCKS5 Bytestream request and
+     * want to define their order. This may be necessary if your application is running on a machine
+     * with multiple network interfaces or if you want to provide your public address in case you
+     * are behind a NAT router.
+     * 
+     * @param addresses the new list of local network addresses
+     */
+    public void replaceLocalAddresses(List<String> addresses) {
+        if (addresses == null) {
+            throw new IllegalArgumentException("list must not be null");
+        }
+        this.localAddresses.clear();
+        this.localAddresses.addAll(addresses);
+
+    }
+
+    /**
+     * Returns the port of the local SOCKS5 proxy server. If it is not running -1 will be returned.
+     * 
+     * @return the port of the local SOCKS5 proxy server or -1 if proxy is not running
+     */
+    public int getPort() {
+        if (!isRunning()) {
+            return -1;
+        }
+        return this.serverSocket.getLocalPort();
+    }
+
+    /**
+     * Returns the socket for the given digest. A socket will be returned if the given digest has
+     * been in the list of allowed transfers (see {@link #addTransfer(String)}) while the peer
+     * connected to the SOCKS5 proxy.
+     * 
+     * @param digest identifying the connection
+     * @return socket or null if there is no socket for the given digest
+     */
+    protected Socket getSocket(String digest) {
+        return this.connectionMap.get(digest);
+    }
+
+    /**
+     * Add the given digest to the list of allowed transfers. Only connections for allowed transfers
+     * are stored and can be retrieved by invoking {@link #getSocket(String)}. All connections to
+     * the local SOCKS5 proxy that don't contain an allowed digest are discarded.
+     * 
+     * @param digest to be added to the list of allowed transfers
+     */
+    protected void addTransfer(String digest) {
+        this.allowedConnections.add(digest);
+    }
+
+    /**
+     * Removes the given digest from the list of allowed transfers. After invoking this method
+     * already stored connections with the given digest will be removed.
+     * <p>
+     * The digest should be removed after establishing the SOCKS5 Bytestream is finished, an error
+     * occurred while establishing the connection or if the connection is not allowed anymore.
+     * 
+     * @param digest to be removed from the list of allowed transfers
+     */
+    protected void removeTransfer(String digest) {
+        this.allowedConnections.remove(digest);
+        this.connectionMap.remove(digest);
+    }
+
+    /**
+     * Returns <code>true</code> if the local SOCKS5 proxy server is running, otherwise
+     * <code>false</code>.
+     * 
+     * @return <code>true</code> if the local SOCKS5 proxy server is running, otherwise
+     *         <code>false</code>
+     */
+    public boolean isRunning() {
+        return this.serverSocket != null;
+    }
+
+    /**
+     * Implementation of a simplified SOCKS5 proxy server.
+     */
+    private class Socks5ServerProcess implements Runnable {
+
+        public void run() {
+            while (true) {
+                Socket socket = null;
+
+                try {
+
+                    if (Socks5Proxy.this.serverSocket.isClosed()
+                                    || Thread.currentThread().isInterrupted()) {
+                        return;
+                    }
+
+                    // accept connection
+                    socket = Socks5Proxy.this.serverSocket.accept();
+
+                    // initialize connection
+                    establishConnection(socket);
+
+                }
+                catch (SocketException e) {
+                    /*
+                     * do nothing, if caused by closing the server socket, thread will terminate in
+                     * next loop
+                     */
+                }
+                catch (Exception e) {
+                    try {
+                        if (socket != null) {
+                            socket.close();
+                        }
+                    }
+                    catch (IOException e1) {
+                        /* do nothing */
+                    }
+                }
+            }
+
+        }
+
+        /**
+         * Negotiates a SOCKS5 connection and stores it on success.
+         * 
+         * @param socket connection to the client
+         * @throws XMPPException if client requests a connection in an unsupported way
+         * @throws IOException if a network error occurred
+         */
+        private void establishConnection(Socket socket) throws XMPPException, IOException {
+            DataOutputStream out = new DataOutputStream(socket.getOutputStream());
+            DataInputStream in = new DataInputStream(socket.getInputStream());
+
+            // first byte is version should be 5
+            int b = in.read();
+            if (b != 5) {
+                throw new XMPPException("Only SOCKS5 supported");
+            }
+
+            // second byte number of authentication methods supported
+            b = in.read();
+
+            // read list of supported authentication methods
+            byte[] auth = new byte[b];
+            in.readFully(auth);
+
+            byte[] authMethodSelectionResponse = new byte[2];
+            authMethodSelectionResponse[0] = (byte) 0x05; // protocol version
+
+            // only authentication method 0, no authentication, supported
+            boolean noAuthMethodFound = false;
+            for (int i = 0; i < auth.length; i++) {
+                if (auth[i] == (byte) 0x00) {
+                    noAuthMethodFound = true;
+                    break;
+                }
+            }
+
+            if (!noAuthMethodFound) {
+                authMethodSelectionResponse[1] = (byte) 0xFF; // no acceptable methods
+                out.write(authMethodSelectionResponse);
+                out.flush();
+                throw new XMPPException("Authentication method not supported");
+            }
+
+            authMethodSelectionResponse[1] = (byte) 0x00; // no-authentication method
+            out.write(authMethodSelectionResponse);
+            out.flush();
+
+            // receive connection request
+            byte[] connectionRequest = Socks5Utils.receiveSocks5Message(in);
+
+            // extract digest
+            String responseDigest = new String(connectionRequest, 5, connectionRequest[4]);
+
+            // return error if digest is not allowed
+            if (!Socks5Proxy.this.allowedConnections.contains(responseDigest)) {
+                connectionRequest[1] = (byte) 0x05; // set return status to 5 (connection refused)
+                out.write(connectionRequest);
+                out.flush();
+
+                throw new XMPPException("Connection is not allowed");
+            }
+
+            connectionRequest[1] = (byte) 0x00; // set return status to 0 (success)
+            out.write(connectionRequest);
+            out.flush();
+
+            // store connection
+            Socks5Proxy.this.connectionMap.put(responseDigest, socket);
+        }
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java
new file mode 100644
index 0000000..9c92563
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/Socks5Utils.java
@@ -0,0 +1,73 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5;
+
+import java.io.DataInputStream;
+import java.io.IOException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * A collection of utility methods for SOcKS5 messages.
+ * 
+ * @author Henning Staib
+ */
+class Socks5Utils {
+
+    /**
+     * Returns a SHA-1 digest of the given parameters as specified in <a
+     * href="http://xmpp.org/extensions/xep-0065.html#impl-socks5">XEP-0065</a>.
+     * 
+     * @param sessionID for the SOCKS5 Bytestream
+     * @param initiatorJID JID of the initiator of a SOCKS5 Bytestream
+     * @param targetJID JID of the target of a SOCKS5 Bytestream
+     * @return SHA-1 digest of the given parameters
+     */
+    public static String createDigest(String sessionID, String initiatorJID, String targetJID) {
+        StringBuilder b = new StringBuilder();
+        b.append(sessionID).append(initiatorJID).append(targetJID);
+        return StringUtils.hash(b.toString());
+    }
+
+    /**
+     * Reads a SOCKS5 message from the given InputStream. The message can either be a SOCKS5 request
+     * message or a SOCKS5 response message.
+     * <p>
+     * (see <a href="http://tools.ietf.org/html/rfc1928">RFC1928</a>)
+     * 
+     * @param in the DataInputStream to read the message from
+     * @return the SOCKS5 message
+     * @throws IOException if a network error occurred
+     * @throws XMPPException if the SOCKS5 message contains an unsupported address type
+     */
+    public static byte[] receiveSocks5Message(DataInputStream in) throws IOException, XMPPException {
+        byte[] header = new byte[5];
+        in.readFully(header, 0, 5);
+
+        if (header[3] != (byte) 0x03) {
+            throw new XMPPException("Unsupported SOCKS5 address type");
+        }
+
+        int addressLength = header[4];
+
+        byte[] response = new byte[7 + addressLength];
+        System.arraycopy(header, 0, response, 0, header.length);
+
+        in.readFully(response, header.length, addressLength + 2);
+
+        return response;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/packet/Bytestream.java b/src/org/jivesoftware/smackx/bytestreams/socks5/packet/Bytestream.java
new file mode 100644
index 0000000..9e07fc3
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/packet/Bytestream.java
@@ -0,0 +1,474 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5.packet;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * A packet representing part of a SOCKS5 Bytestream negotiation.
+ * 
+ * @author Alexander Wenckus
+ */
+public class Bytestream extends IQ {
+
+    private String sessionID;
+
+    private Mode mode = Mode.tcp;
+
+    private final List<StreamHost> streamHosts = new ArrayList<StreamHost>();
+
+    private StreamHostUsed usedHost;
+
+    private Activate toActivate;
+
+    /**
+     * The default constructor
+     */
+    public Bytestream() {
+        super();
+    }
+
+    /**
+     * A constructor where the session ID can be specified.
+     * 
+     * @param SID The session ID related to the negotiation.
+     * @see #setSessionID(String)
+     */
+    public Bytestream(final String SID) {
+        super();
+        setSessionID(SID);
+    }
+
+    /**
+     * Set the session ID related to the bytestream. The session ID is a unique identifier used to
+     * differentiate between stream negotiations.
+     * 
+     * @param sessionID the unique session ID that identifies the transfer.
+     */
+    public void setSessionID(final String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    /**
+     * Returns the session ID related to the bytestream negotiation.
+     * 
+     * @return Returns the session ID related to the bytestream negotiation.
+     * @see #setSessionID(String)
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    /**
+     * Set the transport mode. This should be put in the initiation of the interaction.
+     * 
+     * @param mode the transport mode, either UDP or TCP
+     * @see Mode
+     */
+    public void setMode(final Mode mode) {
+        this.mode = mode;
+    }
+
+    /**
+     * Returns the transport mode.
+     * 
+     * @return Returns the transport mode.
+     * @see #setMode(Mode)
+     */
+    public Mode getMode() {
+        return mode;
+    }
+
+    /**
+     * Adds a potential stream host that the remote user can connect to to receive the file.
+     * 
+     * @param JID The JID of the stream host.
+     * @param address The internet address of the stream host.
+     * @return The added stream host.
+     */
+    public StreamHost addStreamHost(final String JID, final String address) {
+        return addStreamHost(JID, address, 0);
+    }
+
+    /**
+     * Adds a potential stream host that the remote user can connect to to receive the file.
+     * 
+     * @param JID The JID of the stream host.
+     * @param address The internet address of the stream host.
+     * @param port The port on which the remote host is seeking connections.
+     * @return The added stream host.
+     */
+    public StreamHost addStreamHost(final String JID, final String address, final int port) {
+        StreamHost host = new StreamHost(JID, address);
+        host.setPort(port);
+        addStreamHost(host);
+
+        return host;
+    }
+
+    /**
+     * Adds a potential stream host that the remote user can transfer the file through.
+     * 
+     * @param host The potential stream host.
+     */
+    public void addStreamHost(final StreamHost host) {
+        streamHosts.add(host);
+    }
+
+    /**
+     * Returns the list of stream hosts contained in the packet.
+     * 
+     * @return Returns the list of stream hosts contained in the packet.
+     */
+    public Collection<StreamHost> getStreamHosts() {
+        return Collections.unmodifiableCollection(streamHosts);
+    }
+
+    /**
+     * Returns the stream host related to the given JID, or null if there is none.
+     * 
+     * @param JID The JID of the desired stream host.
+     * @return Returns the stream host related to the given JID, or null if there is none.
+     */
+    public StreamHost getStreamHost(final String JID) {
+        if (JID == null) {
+            return null;
+        }
+        for (StreamHost host : streamHosts) {
+            if (host.getJID().equals(JID)) {
+                return host;
+            }
+        }
+
+        return null;
+    }
+
+    /**
+     * Returns the count of stream hosts contained in this packet.
+     * 
+     * @return Returns the count of stream hosts contained in this packet.
+     */
+    public int countStreamHosts() {
+        return streamHosts.size();
+    }
+
+    /**
+     * Upon connecting to the stream host the target of the stream replies to the initiator with the
+     * JID of the SOCKS5 host that they used.
+     * 
+     * @param JID The JID of the used host.
+     */
+    public void setUsedHost(final String JID) {
+        this.usedHost = new StreamHostUsed(JID);
+    }
+
+    /**
+     * Returns the SOCKS5 host connected to by the remote user.
+     * 
+     * @return Returns the SOCKS5 host connected to by the remote user.
+     */
+    public StreamHostUsed getUsedHost() {
+        return usedHost;
+    }
+
+    /**
+     * Returns the activate element of the packet sent to the proxy host to verify the identity of
+     * the initiator and match them to the appropriate stream.
+     * 
+     * @return Returns the activate element of the packet sent to the proxy host to verify the
+     *         identity of the initiator and match them to the appropriate stream.
+     */
+    public Activate getToActivate() {
+        return toActivate;
+    }
+
+    /**
+     * Upon the response from the target of the used host the activate packet is sent to the SOCKS5
+     * proxy. The proxy will activate the stream or return an error after verifying the identity of
+     * the initiator, using the activate packet.
+     * 
+     * @param targetID The JID of the target of the file transfer.
+     */
+    public void setToActivate(final String targetID) {
+        this.toActivate = new Activate(targetID);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<query xmlns=\"http://jabber.org/protocol/bytestreams\"");
+        if (this.getType().equals(IQ.Type.SET)) {
+            if (getSessionID() != null) {
+                buf.append(" sid=\"").append(getSessionID()).append("\"");
+            }
+            if (getMode() != null) {
+                buf.append(" mode = \"").append(getMode()).append("\"");
+            }
+            buf.append(">");
+            if (getToActivate() == null) {
+                for (StreamHost streamHost : getStreamHosts()) {
+                    buf.append(streamHost.toXML());
+                }
+            }
+            else {
+                buf.append(getToActivate().toXML());
+            }
+        }
+        else if (this.getType().equals(IQ.Type.RESULT)) {
+            buf.append(">");
+            if (getUsedHost() != null) {
+                buf.append(getUsedHost().toXML());
+            }
+            // A result from the server can also contain stream hosts
+            else if (countStreamHosts() > 0) {
+                for (StreamHost host : streamHosts) {
+                    buf.append(host.toXML());
+                }
+            }
+        }
+        else if (this.getType().equals(IQ.Type.GET)) {
+            return buf.append("/>").toString();
+        }
+        else {
+            return null;
+        }
+        buf.append("</query>");
+
+        return buf.toString();
+    }
+
+    /**
+     * Packet extension that represents a potential SOCKS5 proxy for the file transfer. Stream hosts
+     * are forwarded to the target of the file transfer who then chooses and connects to one.
+     * 
+     * @author Alexander Wenckus
+     */
+    public static class StreamHost implements PacketExtension {
+
+        public static String NAMESPACE = "";
+
+        public static String ELEMENTNAME = "streamhost";
+
+        private final String JID;
+
+        private final String addy;
+
+        private int port = 0;
+
+        /**
+         * Default constructor.
+         * 
+         * @param JID The JID of the stream host.
+         * @param address The internet address of the stream host.
+         */
+        public StreamHost(final String JID, final String address) {
+            this.JID = JID;
+            this.addy = address;
+        }
+
+        /**
+         * Returns the JID of the stream host.
+         * 
+         * @return Returns the JID of the stream host.
+         */
+        public String getJID() {
+            return JID;
+        }
+
+        /**
+         * Returns the internet address of the stream host.
+         * 
+         * @return Returns the internet address of the stream host.
+         */
+        public String getAddress() {
+            return addy;
+        }
+
+        /**
+         * Sets the port of the stream host.
+         * 
+         * @param port The port on which the potential stream host would accept the connection.
+         */
+        public void setPort(final int port) {
+            this.port = port;
+        }
+
+        /**
+         * Returns the port on which the potential stream host would accept the connection.
+         * 
+         * @return Returns the port on which the potential stream host would accept the connection.
+         */
+        public int getPort() {
+            return port;
+        }
+
+        public String getNamespace() {
+            return NAMESPACE;
+        }
+
+        public String getElementName() {
+            return ELEMENTNAME;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<").append(getElementName()).append(" ");
+            buf.append("jid=\"").append(getJID()).append("\" ");
+            buf.append("host=\"").append(getAddress()).append("\" ");
+            if (getPort() != 0) {
+                buf.append("port=\"").append(getPort()).append("\"");
+            }
+            else {
+                buf.append("zeroconf=\"_jabber.bytestreams\"");
+            }
+            buf.append("/>");
+
+            return buf.toString();
+        }
+    }
+
+    /**
+     * After selected a SOCKS5 stream host and successfully connecting, the target of the file
+     * transfer returns a byte stream packet with the stream host used extension.
+     * 
+     * @author Alexander Wenckus
+     */
+    public static class StreamHostUsed implements PacketExtension {
+
+        public String NAMESPACE = "";
+
+        public static String ELEMENTNAME = "streamhost-used";
+
+        private final String JID;
+
+        /**
+         * Default constructor.
+         * 
+         * @param JID The JID of the selected stream host.
+         */
+        public StreamHostUsed(final String JID) {
+            this.JID = JID;
+        }
+
+        /**
+         * Returns the JID of the selected stream host.
+         * 
+         * @return Returns the JID of the selected stream host.
+         */
+        public String getJID() {
+            return JID;
+        }
+
+        public String getNamespace() {
+            return NAMESPACE;
+        }
+
+        public String getElementName() {
+            return ELEMENTNAME;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<").append(getElementName()).append(" ");
+            buf.append("jid=\"").append(getJID()).append("\" ");
+            buf.append("/>");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * The packet sent by the stream initiator to the stream proxy to activate the connection.
+     * 
+     * @author Alexander Wenckus
+     */
+    public static class Activate implements PacketExtension {
+
+        public String NAMESPACE = "";
+
+        public static String ELEMENTNAME = "activate";
+
+        private final String target;
+
+        /**
+         * Default constructor specifying the target of the stream.
+         * 
+         * @param target The target of the stream.
+         */
+        public Activate(final String target) {
+            this.target = target;
+        }
+
+        /**
+         * Returns the target of the activation.
+         * 
+         * @return Returns the target of the activation.
+         */
+        public String getTarget() {
+            return target;
+        }
+
+        public String getNamespace() {
+            return NAMESPACE;
+        }
+
+        public String getElementName() {
+            return ELEMENTNAME;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<").append(getElementName()).append(">");
+            buf.append(getTarget());
+            buf.append("</").append(getElementName()).append(">");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * The stream can be either a TCP stream or a UDP stream.
+     * 
+     * @author Alexander Wenckus
+     */
+    public enum Mode {
+
+        /**
+         * A TCP based stream.
+         */
+        tcp,
+
+        /**
+         * A UDP based stream.
+         */
+        udp;
+
+        public static Mode fromName(String name) {
+            Mode mode;
+            try {
+                mode = Mode.valueOf(name);
+            }
+            catch (Exception ex) {
+                mode = tcp;
+            }
+
+            return mode;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/bytestreams/socks5/provider/BytestreamsProvider.java b/src/org/jivesoftware/smackx/bytestreams/socks5/provider/BytestreamsProvider.java
new file mode 100644
index 0000000..76f9b0c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/bytestreams/socks5/provider/BytestreamsProvider.java
@@ -0,0 +1,82 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.bytestreams.socks5.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses a bytestream packet.
+ * 
+ * @author Alexander Wenckus
+ */
+public class BytestreamsProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        boolean done = false;
+
+        Bytestream toReturn = new Bytestream();
+
+        String id = parser.getAttributeValue("", "sid");
+        String mode = parser.getAttributeValue("", "mode");
+
+        // streamhost
+        String JID = null;
+        String host = null;
+        String port = null;
+
+        int eventType;
+        String elementName;
+        while (!done) {
+            eventType = parser.next();
+            elementName = parser.getName();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (elementName.equals(Bytestream.StreamHost.ELEMENTNAME)) {
+                    JID = parser.getAttributeValue("", "jid");
+                    host = parser.getAttributeValue("", "host");
+                    port = parser.getAttributeValue("", "port");
+                }
+                else if (elementName.equals(Bytestream.StreamHostUsed.ELEMENTNAME)) {
+                    toReturn.setUsedHost(parser.getAttributeValue("", "jid"));
+                }
+                else if (elementName.equals(Bytestream.Activate.ELEMENTNAME)) {
+                    toReturn.setToActivate(parser.getAttributeValue("", "jid"));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (elementName.equals("streamhost")) {
+                    if (port == null) {
+                        toReturn.addStreamHost(JID, host);
+                    }
+                    else {
+                        toReturn.addStreamHost(JID, host, Integer.parseInt(port));
+                    }
+                    JID = null;
+                    host = null;
+                    port = null;
+                }
+                else if (elementName.equals("query")) {
+                    done = true;
+                }
+            }
+        }
+
+        toReturn.setMode((Bytestream.Mode.fromName(mode)));
+        toReturn.setSessionID(id);
+        return toReturn;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/carbons/Carbon.java b/src/org/jivesoftware/smackx/carbons/Carbon.java
new file mode 100644
index 0000000..588688a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/carbons/Carbon.java
@@ -0,0 +1,139 @@
+/**
+ * Copyright 2013 Georg Lukas
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.carbons;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.forward.Forwarded;
+import org.jivesoftware.smackx.packet.DelayInfo;
+import org.jivesoftware.smackx.provider.DelayInfoProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Packet extension for XEP-0280: Message Carbons. This class implements
+ * the packet extension and a {@link PacketExtensionProvider} to parse
+ * message carbon copies from a packet. The extension
+ * <a href="http://xmpp.org/extensions/xep-0280.html">XEP-0280</a> is
+ * meant to synchronize a message flow to multiple presences of a user.
+ *
+ * <p>The {@link Carbon.Provider} must be registered in the
+ * <b>smack.properties</b> file for the elements <b>sent</b> and
+ * <b>received</b> with namespace <b>urn:xmpp:carbons:2</b></p> to be used.
+ *
+ * @author Georg Lukas
+ */
+public class Carbon implements PacketExtension {
+    public static final String NAMESPACE = "urn:xmpp:carbons:2";
+
+    private Direction dir;
+    private Forwarded fwd;
+
+    public Carbon(Direction dir, Forwarded fwd) {
+        this.dir = dir;
+        this.fwd = fwd;
+    }
+
+    /**
+     * get the direction (sent or received) of the carbon.
+     *
+     * @return the {@link Direction} of the carbon.
+     */
+    public Direction getDirection() {
+        return dir;
+    }
+
+    /**
+     * get the forwarded packet.
+     *
+     * @return the {@link Forwarded} message contained in this Carbon.
+     */
+    public Forwarded getForwarded() {
+        return fwd;
+    }
+
+    @Override
+    public String getElementName() {
+        return dir.toString();
+    }
+
+    @Override
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    @Override
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"")
+                .append(getNamespace()).append("\">");
+
+        buf.append(fwd.toXML());
+
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * An enum to display the direction of a {@link Carbon} message.
+     */
+    public static enum Direction {
+        received,
+        sent
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            Direction dir = Direction.valueOf(parser.getName());
+            Forwarded fwd = null;
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG && parser.getName().equals("forwarded")) {
+                    fwd = (Forwarded)new Forwarded.Provider().parseExtension(parser);
+                }
+                else if (eventType == XmlPullParser.END_TAG && dir == Direction.valueOf(parser.getName()))
+                    done = true;
+            }
+            if (fwd == null)
+                throw new Exception("sent/received must contain exactly one <forwarded> tag");
+            return new Carbon(dir, fwd);
+        }
+    }
+
+    /**
+     * Packet extension indicating that a message may not be carbon-copied.
+     */
+    public static class Private implements PacketExtension {
+        public static final String ELEMENT = "private";
+
+        public String getElementName() {
+            return ELEMENT;
+        }
+
+        public String getNamespace() {
+            return Carbon.NAMESPACE;
+        }
+
+        public String toXML() {
+            return "<" + ELEMENT + " xmlns=\"" + Carbon.NAMESPACE + "\"/>";
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/carbons/CarbonManager.java b/src/org/jivesoftware/smackx/carbons/CarbonManager.java
new file mode 100644
index 0000000..f44701a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/carbons/CarbonManager.java
@@ -0,0 +1,213 @@
+/**
+ * Copyright 2013 Georg Lukas
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.carbons;
+
+import java.util.Collections;
+import java.util.Map;
+import java.util.WeakHashMap;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+
+/**
+ * Packet extension for XEP-0280: Message Carbons. This class implements
+ * the manager for registering {@link Carbon} support, enabling and disabling
+ * message carbons.
+ *
+ * You should call enableCarbons() before sending your first undirected
+ * presence.
+ *
+ * @author Georg Lukas
+ */
+public class CarbonManager {
+
+    private static Map<Connection, CarbonManager> instances =
+            Collections.synchronizedMap(new WeakHashMap<Connection, CarbonManager>());
+
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new CarbonManager(connection);
+            }
+        });
+    }
+    
+    private Connection connection;
+    private volatile boolean enabled_state = false;
+
+    private CarbonManager(Connection connection) {
+        ServiceDiscoveryManager sdm = ServiceDiscoveryManager.getInstanceFor(connection);
+        sdm.addFeature(Carbon.NAMESPACE);
+        this.connection = connection;
+        instances.put(connection, this);
+    }
+
+    /**
+     * Obtain the CarbonManager responsible for a connection.
+     *
+     * @param connection the connection object.
+     *
+     * @return a CarbonManager instance
+     */
+    public static CarbonManager getInstanceFor(Connection connection) {
+        CarbonManager carbonManager = instances.get(connection);
+
+        if (carbonManager == null) {
+            carbonManager = new CarbonManager(connection);
+        }
+
+        return carbonManager;
+    }
+
+    private IQ carbonsEnabledIQ(final boolean new_state) {
+        IQ setIQ = new IQ() {
+            public String getChildElementXML() {
+                return "<" + (new_state? "enable" : "disable") + " xmlns='" + Carbon.NAMESPACE + "'/>";
+            }
+        };
+        setIQ.setType(IQ.Type.SET);
+        return setIQ;
+    }
+
+    /**
+     * Returns true if XMPP Carbons are supported by the server.
+     * 
+     * @return true if supported
+     */
+    public boolean isSupportedByServer() {
+        try {
+            DiscoverInfo result = ServiceDiscoveryManager
+                .getInstanceFor(connection).discoverInfo(connection.getServiceName());
+            return result.containsFeature(Carbon.NAMESPACE);
+        }
+        catch (XMPPException e) {
+            return false;
+        }
+    }
+
+    /**
+     * Notify server to change the carbons state. This method returns
+     * immediately and changes the variable when the reply arrives.
+     *
+     * You should first check for support using isSupportedByServer().
+     *
+     * @param new_state whether carbons should be enabled or disabled
+     */
+    public void sendCarbonsEnabled(final boolean new_state) {
+        IQ setIQ = carbonsEnabledIQ(new_state);
+
+        connection.addPacketListener(new PacketListener() {
+            public void processPacket(Packet packet) {
+                IQ result = (IQ)packet;
+                if (result.getType() == IQ.Type.RESULT) {
+                    enabled_state = new_state;
+                }
+                connection.removePacketListener(this);
+            }
+        }, new PacketIDFilter(setIQ.getPacketID()));
+
+        connection.sendPacket(setIQ);
+    }
+
+    /**
+     * Notify server to change the carbons state. This method blocks
+     * some time until the server replies to the IQ and returns true on
+     * success.
+     *
+     * You should first check for support using isSupportedByServer().
+     *
+     * @param new_state whether carbons should be enabled or disabled
+     *
+     * @return true if the operation was successful
+     */
+    public boolean setCarbonsEnabled(final boolean new_state) {
+        if (enabled_state == new_state)
+            return true;
+
+        IQ setIQ = carbonsEnabledIQ(new_state);
+
+        PacketCollector collector =
+                connection.createPacketCollector(new PacketIDFilter(setIQ.getPacketID()));
+        connection.sendPacket(setIQ);
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+
+        if (result != null && result.getType() == IQ.Type.RESULT) {
+            enabled_state = new_state;
+            return true;
+        }
+        return false;
+    }
+
+    /**
+     * Helper method to enable carbons.
+     *
+     * @return true if the operation was successful
+     */
+    public boolean enableCarbons() {
+        return setCarbonsEnabled(true);
+    }
+
+    /**
+     * Helper method to disable carbons.
+     *
+     * @return true if the operation was successful
+     */
+    public boolean disableCarbons() {
+        return setCarbonsEnabled(false);
+    }
+
+    /**
+     * Check if carbons are enabled on this connection.
+     */
+    public boolean getCarbonsEnabled() {
+        return this.enabled_state;
+    }
+
+    /**
+     * Obtain a Carbon from a message, if available.
+     *
+     * @param msg Message object to check for carbons
+     *
+     * @return a Carbon if available, null otherwise.
+     */
+    public static Carbon getCarbon(Message msg) {
+        Carbon cc = (Carbon)msg.getExtension("received", Carbon.NAMESPACE);
+        if (cc == null)
+            cc = (Carbon)msg.getExtension("sent", Carbon.NAMESPACE);
+        return cc;
+    }
+
+    /**
+     * Mark a message as "private", so it will not be carbon-copied.
+     *
+     * @param msg Message object to mark private
+     */
+    public static void disableCarbons(Message msg) {
+        msg.addExtension(new Carbon.Private());
+    }
+}
diff --git a/src/org/jivesoftware/smackx/commands/AdHocCommand.java b/src/org/jivesoftware/smackx/commands/AdHocCommand.java
new file mode 100755
index 0000000..3077d08
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/AdHocCommand.java
@@ -0,0 +1,450 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.commands;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.packet.AdHocCommandData;
+
+import java.util.List;
+
+/**
+ * An ad-hoc command is responsible for executing the provided service and
+ * storing the result of the execution. Each new request will create a new
+ * instance of the command, allowing information related to executions to be
+ * stored in it. For example suppose that a command that retrieves the list of
+ * users on a server is implemented. When the command is executed it gets that
+ * list and the result is stored as a form in the command instance, i.e. the
+ * <code>getForm</code> method retrieves a form with all the users.
+ * <p>
+ * Each command has a <tt>node</tt> that should be unique within a given JID.
+ * <p>
+ * Commands may have zero or more stages. Each stage is usually used for
+ * gathering information required for the command execution. Users are able to
+ * move forward or backward across the different stages. Commands may not be
+ * cancelled while they are being executed. However, users may request the
+ * "cancel" action when submitting a stage response indicating that the command
+ * execution should be aborted. Thus, releasing any collected information.
+ * Commands that require user interaction (i.e. have more than one stage) will
+ * have to provide the data forms the user must complete in each stage and the
+ * allowed actions the user might perform during each stage (e.g. go to the
+ * previous stage or go to the next stage).
+ * <p>
+ * All the actions may throw an XMPPException if there is a problem executing
+ * them. The <code>XMPPError</code> of that exception may have some specific
+ * information about the problem. The possible extensions are:
+ * 
+ * <li><i>malformed-action</i>. Extension of a <i>bad-request</i> error.</li>
+ * <li><i>bad-action</i>. Extension of a <i>bad-request</i> error.</li>
+ * <li><i>bad-locale</i>. Extension of a <i>bad-request</i> error.</li>
+ * <li><i>bad-payload</i>. Extension of a <i>bad-request</i> error.</li>
+ * <li><i>bad-sessionid</i>. Extension of a <i>bad-request</i> error.</li>
+ * <li><i>session-expired</i>. Extension of a <i>not-allowed</i> error.</li>
+ * <p>
+ * See the <code>SpecificErrorCondition</code> class for detailed description
+ * of each one.
+ * <p>
+ * Use the <code>getSpecificErrorConditionFrom</code> to obtain the specific
+ * information from an <code>XMPPError</code>.
+ * 
+ * @author Gabriel Guardincerri
+ * 
+ */
+public abstract class AdHocCommand {
+    // TODO: Analyze the redesign of command by having an ExecutionResponse as a
+    // TODO: result to the execution of every action. That result should have all the
+    // TODO: information related to the execution, e.g. the form to fill. Maybe this
+    // TODO: design is more intuitive and simpler than the current one that has all in
+    // TODO: one class.
+
+    private AdHocCommandData data;
+
+    public AdHocCommand() {
+        super();
+        data = new AdHocCommandData();
+    }
+
+    /**
+     * Returns the specific condition of the <code>error</code> or <tt>null</tt> if the
+     * error doesn't have any.
+     * 
+     * @param error the error the get the specific condition from.
+     * @return the specific condition of this error, or null if it doesn't have
+     *         any.
+     */
+    public static SpecificErrorCondition getSpecificErrorCondition(XMPPError error) {
+        // This method is implemented to provide an easy way of getting a packet
+        // extension of the XMPPError.
+        for (SpecificErrorCondition condition : SpecificErrorCondition.values()) {
+            if (error.getExtension(condition.toString(),
+                    AdHocCommandData.SpecificError.namespace) != null) {
+                return condition;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Set the the human readable name of the command, usually used for
+     * displaying in a UI.
+     * 
+     * @param name the name.
+     */
+    public void setName(String name) {
+        data.setName(name);
+    }
+
+    /**
+     * Returns the human readable name of the command.
+     * 
+     * @return the human readable name of the command
+     */
+    public String getName() {
+        return data.getName();
+    }
+
+    /**
+     * Sets the unique identifier of the command. This value must be unique for
+     * the <code>OwnerJID</code>.
+     * 
+     * @param node the unique identifier of the command.
+     */
+    public void setNode(String node) {
+        data.setNode(node);
+    }
+
+    /**
+     * Returns the unique identifier of the command. It is unique for the
+     * <code>OwnerJID</code>.
+     * 
+     * @return the unique identifier of the command.
+     */
+    public String getNode() {
+        return data.getNode();
+    }
+
+    /**
+     * Returns the full JID of the owner of this command. This JID is the "to" of a
+     * execution request.
+     * 
+     * @return the owner JID.
+     */
+    public abstract String getOwnerJID();
+
+    /**
+     * Returns the notes that the command has at the current stage.
+     * 
+     * @return a list of notes.
+     */
+    public List<AdHocCommandNote> getNotes() {
+        return data.getNotes();
+    }
+
+    /**
+     * Adds a note to the current stage. This should be used when setting a
+     * response to the execution of an action. All the notes added here are
+     * returned by the {@link #getNotes} method during the current stage.
+     * Once the stage changes all the notes are discarded.
+     * 
+     * @param note the note.
+     */
+    protected void addNote(AdHocCommandNote note) {
+        data.addNote(note);
+    }
+
+    public String getRaw() {
+        return data.getChildElementXML();
+    }
+
+    /**
+     * Returns the form of the current stage. Usually it is the form that must
+     * be answered to execute the next action. If that is the case it should be
+     * used by the requester to fill all the information that the executor needs
+     * to continue to the next stage. It can also be the result of the
+     * execution.
+     * 
+     * @return the form of the current stage to fill out or the result of the
+     *         execution.
+     */
+    public Form getForm() {
+        if (data.getForm() == null) {
+            return null;
+        }
+        else {
+            return new Form(data.getForm());
+        }
+    }
+
+    /**
+     * Sets the form of the current stage. This should be used when setting a
+     * response. It could be a form to fill out the information needed to go to
+     * the next stage or the result of an execution.
+     * 
+     * @param form the form of the current stage to fill out or the result of the
+     *      execution.
+     */
+    protected void setForm(Form form) {
+        data.setForm(form.getDataFormToSend());
+    }
+
+    /**
+     * Executes the command. This is invoked only on the first stage of the
+     * command. It is invoked on every command. If there is a problem executing
+     * the command it throws an XMPPException.
+     * 
+     * @throws XMPPException if there is an error executing the command.
+     */
+    public abstract void execute() throws XMPPException;
+
+    /**
+     * Executes the next action of the command with the information provided in
+     * the <code>response</code>. This form must be the answer form of the
+     * previous stage. This method will be only invoked for commands that have one
+     * or more stages. If there is a problem executing the command it throws an
+     * XMPPException.
+     * 
+     * @param response the form answer of the previous stage.
+     * @throws XMPPException if there is a problem executing the command.
+     */
+    public abstract void next(Form response) throws XMPPException;
+
+    /**
+     * Completes the command execution with the information provided in the
+     * <code>response</code>. This form must be the answer form of the
+     * previous stage. This method will be only invoked for commands that have one
+     * or more stages. If there is a problem executing the command it throws an
+     * XMPPException.
+     * 
+     * @param response the form answer of the previous stage.
+     * @throws XMPPException if there is a problem executing the command.
+     */
+    public abstract void complete(Form response) throws XMPPException;
+
+    /**
+     * Goes to the previous stage. The requester is asking to re-send the
+     * information of the previous stage. The command must change it state to
+     * the previous one. If there is a problem executing the command it throws
+     * an XMPPException.
+     * 
+     * @throws XMPPException if there is a problem executing the command.
+     */
+    public abstract void prev() throws XMPPException;
+
+    /**
+     * Cancels the execution of the command. This can be invoked on any stage of
+     * the execution. If there is a problem executing the command it throws an
+     * XMPPException.
+     * 
+     * @throws XMPPException if there is a problem executing the command.
+     */
+    public abstract void cancel() throws XMPPException;
+
+    /**
+     * Returns a collection with the allowed actions based on the current stage.
+     * Possible actions are: {@link Action#prev prev}, {@link Action#next next} and
+     * {@link Action#complete complete}. This method will be only invoked for commands that
+     * have one or more stages.
+     * 
+     * @return a collection with the allowed actions based on the current stage
+     *      as defined in the SessionData.
+     */
+    protected List<Action> getActions() {
+        return data.getActions();
+    }
+
+    /**
+     * Add an action to the current stage available actions. This should be used
+     * when creating a response.
+     * 
+     * @param action the action.
+     */
+    protected void addActionAvailable(Action action) {
+        data.addAction(action);
+    }
+
+    /**
+     * Returns the action available for the current stage which is
+     * considered the equivalent to "execute". When the requester sends his
+     * reply, if no action was defined in the command then the action will be
+     * assumed "execute" thus assuming the action returned by this method. This
+     * method will never be invoked for commands that have no stages.
+     * 
+     * @return the action available for the current stage which is considered
+     *      the equivalent to "execute".
+     */
+    protected Action getExecuteAction() {
+        return data.getExecuteAction();
+    }
+
+    /**
+     * Sets which of the actions available for the current stage is
+     * considered the equivalent to "execute". This should be used when setting
+     * a response. When the requester sends his reply, if no action was defined
+     * in the command then the action will be assumed "execute" thus assuming
+     * the action returned by this method.
+     * 
+     * @param action the action.
+     */
+    protected void setExecuteAction(Action action) {
+        data.setExecuteAction(action);
+    }
+
+    /**
+     * Returns the status of the current stage.
+     * 
+     * @return the current status.
+     */
+    public Status getStatus() {
+        return data.getStatus();
+    }
+
+    /**
+     * Sets the data of the current stage. This should not used.
+     * 
+     * @param data the data.
+     */
+    void setData(AdHocCommandData data) {
+        this.data = data;
+    }
+
+    /**
+     * Gets the data of the current stage. This should not used.
+     *
+     * @return the data.
+     */
+    AdHocCommandData getData() {
+        return data;
+    }
+
+    /**
+     * Returns true if the <code>action</code> is available in the current stage.
+     * The {@link Action#cancel cancel} action is always allowed. To define the
+     * available actions use the <code>addActionAvailable</code> method.
+     * 
+     * @param action
+     *            The action to check if it is available.
+     * @return True if the action is available for the current stage.
+     */
+    protected boolean isValidAction(Action action) {
+        return getActions().contains(action) || Action.cancel.equals(action);
+    }
+
+    /**
+     * The status of the stage in the adhoc command.
+     */
+    public enum Status {
+
+        /**
+         * The command is being executed.
+         */
+        executing,
+
+        /**
+         * The command has completed. The command session has ended.
+         */
+        completed,
+
+        /**
+         * The command has been canceled. The command session has ended.
+         */
+        canceled
+    }
+
+    public enum Action {
+
+        /**
+         * The command should be executed or continue to be executed. This is
+         * the default value.
+         */
+        execute,
+
+        /**
+         * The command should be canceled.
+         */
+        cancel,
+
+        /**
+         * The command should be digress to the previous stage of execution.
+         */
+        prev,
+
+        /**
+         * The command should progress to the next stage of execution.
+         */
+        next,
+
+        /**
+         * The command should be completed (if possible).
+         */
+        complete,
+
+        /**
+         * The action is unknow. This is used when a recieved message has an
+         * unknown action. It must not be used to send an execution request.
+         */
+        unknown
+    }
+
+    public enum SpecificErrorCondition {
+
+        /**
+         * The responding JID cannot accept the specified action.
+         */
+        badAction("bad-action"),
+
+        /**
+         * The responding JID does not understand the specified action.
+         */
+        malformedAction("malformed-action"),
+
+        /**
+         * The responding JID cannot accept the specified language/locale.
+         */
+        badLocale("bad-locale"),
+
+        /**
+         * The responding JID cannot accept the specified payload (e.g. the data
+         * form did not provide one or more required fields).
+         */
+        badPayload("bad-payload"),
+
+        /**
+         * The responding JID cannot accept the specified sessionid.
+         */
+        badSessionid("bad-sessionid"),
+
+        /**
+         * The requesting JID specified a sessionid that is no longer active
+         * (either because it was completed, canceled, or timed out).
+         */
+        sessionExpired("session-expired");
+
+        private String value;
+
+        SpecificErrorCondition(String value) {
+            this.value = value;
+        }
+
+        public String toString() {
+            return value;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/commands/AdHocCommandManager.java b/src/org/jivesoftware/smackx/commands/AdHocCommandManager.java
new file mode 100755
index 0000000..8dac999
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/AdHocCommandManager.java
@@ -0,0 +1,753 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2008 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.commands;
+
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.NodeInformationProvider;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.commands.AdHocCommand.Action;
+import org.jivesoftware.smackx.commands.AdHocCommand.Status;
+import org.jivesoftware.smackx.packet.AdHocCommandData;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * An AdHocCommandManager is responsible for keeping the list of available
+ * commands offered by a service and for processing commands requests.
+ *
+ * Pass in a Connection instance to
+ * {@link #getAddHocCommandsManager(org.jivesoftware.smack.Connection)} in order to
+ * get an instance of this class. 
+ * 
+ * @author Gabriel Guardincerri
+ */
+public class AdHocCommandManager {
+
+    private static final String DISCO_NAMESPACE = "http://jabber.org/protocol/commands";
+
+    private static final String discoNode = DISCO_NAMESPACE;
+
+    /**
+     * The session time out in seconds.
+     */
+    private static final int SESSION_TIMEOUT = 2 * 60;
+
+    /**
+     * Map a Connection with it AdHocCommandManager. This map have a key-value
+     * pair for every active connection.
+     */
+    private static Map<Connection, AdHocCommandManager> instances =
+            new ConcurrentHashMap<Connection, AdHocCommandManager>();
+
+    /**
+     * Register the listener for all the connection creations. When a new
+     * connection is created a new AdHocCommandManager is also created and
+     * related to that connection.
+     */
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new AdHocCommandManager(connection);
+            }
+        });
+    }
+
+    /**
+     * Returns the <code>AdHocCommandManager</code> related to the
+     * <code>connection</code>.
+     *
+     * @param connection the XMPP connection.
+     * @return the AdHocCommandManager associated with the connection.
+     */
+    public static AdHocCommandManager getAddHocCommandsManager(Connection connection) {
+        return instances.get(connection);
+    }
+
+    /**
+     * Thread that reaps stale sessions.
+     */
+    private Thread sessionsSweeper;
+
+    /**
+     * The Connection that this instances of AdHocCommandManager manages
+     */
+    private Connection connection;
+
+    /**
+     * Map a command node with its AdHocCommandInfo. Note: Key=command node,
+     * Value=command. Command node matches the node attribute sent by command
+     * requesters.
+     */
+    private Map<String, AdHocCommandInfo> commands = Collections
+            .synchronizedMap(new WeakHashMap<String, AdHocCommandInfo>());
+
+    /**
+     * Map a command session ID with the instance LocalCommand. The LocalCommand
+     * is the an objects that has all the information of the current state of
+     * the command execution. Note: Key=session ID, Value=LocalCommand. Session
+     * ID matches the sessionid attribute sent by command responders.
+     */
+    private Map<String, LocalCommand> executingCommands = new ConcurrentHashMap<String, LocalCommand>();
+
+    private AdHocCommandManager(Connection connection) {
+        super();
+        this.connection = connection;
+        init();
+    }
+
+    /**
+     * Registers a new command with this command manager, which is related to a
+     * connection. The <tt>node</tt> is an unique identifier of that command for
+     * the connection related to this command manager. The <tt>name</tt> is the
+     * human readable name of the command. The <tt>class</tt> is the class of
+     * the command, which must extend {@link LocalCommand} and have a default
+     * constructor.
+     *
+     * @param node the unique identifier of the command.
+     * @param name the human readable name of the command.
+     * @param clazz the class of the command, which must extend {@link LocalCommand}.
+     */
+    public void registerCommand(String node, String name, final Class<? extends LocalCommand> clazz) {
+        registerCommand(node, name, new LocalCommandFactory() {
+            public LocalCommand getInstance() throws InstantiationException, IllegalAccessException  {
+                return clazz.newInstance();
+            }
+        });
+    }
+
+    /**
+     * Registers a new command with this command manager, which is related to a
+     * connection. The <tt>node</tt> is an unique identifier of that
+     * command for the connection related to this command manager. The <tt>name</tt>
+     * is the human readeale name of the command. The <tt>factory</tt> generates
+     * new instances of the command.
+     *
+     * @param node the unique identifier of the command.
+     * @param name the human readable name of the command.
+     * @param factory a factory to create new instances of the command.
+     */
+    public void registerCommand(String node, final String name, LocalCommandFactory factory) {
+        AdHocCommandInfo commandInfo = new AdHocCommandInfo(node, name, connection.getUser(), factory);
+
+        commands.put(node, commandInfo);
+        // Set the NodeInformationProvider that will provide information about
+        // the added command
+        ServiceDiscoveryManager.getInstanceFor(connection).setNodeInformationProvider(node,
+                new NodeInformationProvider() {
+                    public List<DiscoverItems.Item> getNodeItems() {
+                        return null;
+                    }
+
+                    public List<String> getNodeFeatures() {
+                        List<String> answer = new ArrayList<String>();
+                        answer.add(DISCO_NAMESPACE);
+                        // TODO: check if this service is provided by the
+                        // TODO: current connection.
+                        answer.add("jabber:x:data");
+                        return answer;
+                    }
+
+                    public List<DiscoverInfo.Identity> getNodeIdentities() {
+                        List<DiscoverInfo.Identity> answer = new ArrayList<DiscoverInfo.Identity>();
+                        DiscoverInfo.Identity identity = new DiscoverInfo.Identity(
+                                "automation", name, "command-node");
+                        answer.add(identity);
+                        return answer;
+                    }
+
+                    @Override
+                    public List<PacketExtension> getNodePacketExtensions() {
+                        return null;
+                    }
+
+                });
+    }
+
+    /**
+     * Discover the commands of an specific JID. The <code>jid</code> is a
+     * full JID.
+     *
+     * @param jid the full JID to retrieve the commands for.
+     * @return the discovered items.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public DiscoverItems discoverCommands(String jid) throws XMPPException {
+        ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager
+                .getInstanceFor(connection);
+        return serviceDiscoveryManager.discoverItems(jid, discoNode);
+    }
+
+    /**
+     * Publish the commands to an specific JID.
+     *
+     * @param jid the full JID to publish the commands to.
+     * @throws XMPPException if the operation failed for some reason.
+     */
+    public void publishCommands(String jid) throws XMPPException {
+        ServiceDiscoveryManager serviceDiscoveryManager = ServiceDiscoveryManager
+                .getInstanceFor(connection);
+
+        // Collects the commands to publish as items
+        DiscoverItems discoverItems = new DiscoverItems();
+        Collection<AdHocCommandInfo> xCommandsList = getRegisteredCommands();
+
+        for (AdHocCommandInfo info : xCommandsList) {
+            DiscoverItems.Item item = new DiscoverItems.Item(info.getOwnerJID());
+            item.setName(info.getName());
+            item.setNode(info.getNode());
+            discoverItems.addItem(item);
+        }
+
+        serviceDiscoveryManager.publishItems(jid, discoNode, discoverItems);
+    }
+
+    /**
+     * Returns a command that represents an instance of a command in a remote
+     * host. It is used to execute remote commands. The concept is similar to
+     * RMI. Every invocation on this command is equivalent to an invocation in
+     * the remote command.
+     *
+     * @param jid the full JID of the host of the remote command
+     * @param node the identifier of the command
+     * @return a local instance equivalent to the remote command.
+     */
+    public RemoteCommand getRemoteCommand(String jid, String node) {
+        return new RemoteCommand(connection, node, jid);
+    }
+
+    /**
+     * <ul>
+     * <li>Adds listeners to the connection</li>
+     * <li>Registers the ad-hoc command feature to the ServiceDiscoveryManager</li>
+     * <li>Registers the items of the feature</li>
+     * <li>Adds packet listeners to handle execution requests</li>
+     * <li>Creates and start the session sweeper</li>
+     * </ul>
+     */
+    private void init() {
+        // Register the new instance and associate it with the connection
+        instances.put(connection, this);
+
+        // Add a listener to the connection that removes the registered instance
+        // when the connection is closed
+        connection.addConnectionListener(new ConnectionListener() {
+            public void connectionClosed() {
+                // Unregister this instance since the connection has been closed
+                instances.remove(connection);
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                // Unregister this instance since the connection has been closed
+                instances.remove(connection);
+            }
+
+            public void reconnectionSuccessful() {
+                // Register this instance since the connection has been
+                // reestablished
+                instances.put(connection, AdHocCommandManager.this);
+            }
+
+            public void reconnectingIn(int seconds) {
+                // Nothing to do
+            }
+
+            public void reconnectionFailed(Exception e) {
+                // Nothing to do
+            }
+        });
+
+        // Add the feature to the service discovery manage to show that this
+        // connection supports the AdHoc-Commands protocol.
+        // This information will be used when another client tries to
+        // discover whether this client supports AdHoc-Commands or not.
+        ServiceDiscoveryManager.getInstanceFor(connection).addFeature(
+                DISCO_NAMESPACE);
+
+        // Set the NodeInformationProvider that will provide information about
+        // which AdHoc-Commands are registered, whenever a disco request is
+        // received
+        ServiceDiscoveryManager.getInstanceFor(connection)
+                .setNodeInformationProvider(discoNode,
+                        new NodeInformationProvider() {
+                            public List<DiscoverItems.Item> getNodeItems() {
+
+                                List<DiscoverItems.Item> answer = new ArrayList<DiscoverItems.Item>();
+                                Collection<AdHocCommandInfo> commandsList = getRegisteredCommands();
+
+                                for (AdHocCommandInfo info : commandsList) {
+                                    DiscoverItems.Item item = new DiscoverItems.Item(
+                                            info.getOwnerJID());
+                                    item.setName(info.getName());
+                                    item.setNode(info.getNode());
+                                    answer.add(item);
+                                }
+
+                                return answer;
+                            }
+
+                            public List<String> getNodeFeatures() {
+                                return null;
+                            }
+
+                            public List<Identity> getNodeIdentities() {
+                                return null;
+                            }
+
+                            @Override
+                            public List<PacketExtension> getNodePacketExtensions() {
+                                return null;
+                            }
+                        });
+
+        // The packet listener and the filter for processing some AdHoc Commands
+        // Packets
+        PacketListener listener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                AdHocCommandData requestData = (AdHocCommandData) packet;
+                processAdHocCommand(requestData);
+            }
+        };
+
+        PacketFilter filter = new PacketTypeFilter(AdHocCommandData.class);
+        connection.addPacketListener(listener, filter);
+
+        sessionsSweeper = null;
+    }
+
+    /**
+     * Process the AdHoc-Command packet that request the execution of some
+     * action of a command. If this is the first request, this method checks,
+     * before executing the command, if:
+     * <ul>
+     *  <li>The requested command exists</li>
+     *  <li>The requester has permissions to execute it</li>
+     *  <li>The command has more than one stage, if so, it saves the command and
+     *      session ID for further use</li>
+     * </ul>
+     * 
+     * <br>
+     * <br>
+     * If this is not the first request, this method checks, before executing
+     * the command, if:
+     * <ul>
+     *  <li>The session ID of the request was stored</li>
+     *  <li>The session life do not exceed the time out</li>
+     *  <li>The action to execute is one of the available actions</li>
+     * </ul>
+     *
+     * @param requestData
+     *            the packet to process.
+     */
+    private void processAdHocCommand(AdHocCommandData requestData) {
+        // Only process requests of type SET
+        if (requestData.getType() != IQ.Type.SET) {
+            return;
+        }
+
+        // Creates the response with the corresponding data
+        AdHocCommandData response = new AdHocCommandData();
+        response.setTo(requestData.getFrom());
+        response.setPacketID(requestData.getPacketID());
+        response.setNode(requestData.getNode());
+        response.setId(requestData.getTo());
+
+        String sessionId = requestData.getSessionID();
+        String commandNode = requestData.getNode();
+
+        if (sessionId == null) {
+            // A new execution request has been received. Check that the
+            // command exists
+            if (!commands.containsKey(commandNode)) {
+                // Requested command does not exist so return
+                // item_not_found error.
+                respondError(response, XMPPError.Condition.item_not_found);
+                return;
+            }
+
+            // Create new session ID
+            sessionId = StringUtils.randomString(15);
+
+            try {
+                // Create a new instance of the command with the
+                // corresponding sessioid
+                LocalCommand command = newInstanceOfCmd(commandNode, sessionId);
+
+                response.setType(IQ.Type.RESULT);
+                command.setData(response);
+
+                // Check that the requester has enough permission.
+                // Answer forbidden error if requester permissions are not
+                // enough to execute the requested command
+                if (!command.hasPermission(requestData.getFrom())) {
+                    respondError(response, XMPPError.Condition.forbidden);
+                    return;
+                }
+
+                Action action = requestData.getAction();
+
+                // If the action is unknown then respond an error.
+                if (action != null && action.equals(Action.unknown)) {
+                    respondError(response, XMPPError.Condition.bad_request,
+                            AdHocCommand.SpecificErrorCondition.malformedAction);
+                    return;
+                }
+
+                // If the action is not execute, then it is an invalid action.
+                if (action != null && !action.equals(Action.execute)) {
+                    respondError(response, XMPPError.Condition.bad_request,
+                            AdHocCommand.SpecificErrorCondition.badAction);
+                    return;
+                }
+
+                // Increase the state number, so the command knows in witch
+                // stage it is
+                command.incrementStage();
+                // Executes the command
+                command.execute();
+
+                if (command.isLastStage()) {
+                    // If there is only one stage then the command is completed
+                    response.setStatus(Status.completed);
+                }
+                else {
+                    // Else it is still executing, and is registered to be
+                    // available for the next call
+                    response.setStatus(Status.executing);
+                    executingCommands.put(sessionId, command);
+                    // See if the session reaping thread is started. If not, start it.
+                    if (sessionsSweeper == null) {
+                        sessionsSweeper = new Thread(new Runnable() {
+                            public void run() {
+                                while (true) {
+                                    for (String sessionId : executingCommands.keySet()) {
+                                        LocalCommand command = executingCommands.get(sessionId);
+                                        // Since the command could be removed in the meanwhile
+                                        // of getting the key and getting the value - by a
+                                        // processed packet. We must check if it still in the
+                                        // map.
+                                        if (command != null) {
+                                            long creationStamp = command.getCreationDate();
+                                            // Check if the Session data has expired (default is
+                                            // 10 minutes)
+                                            // To remove it from the session list it waits for
+                                            // the double of the of time out time. This is to
+                                            // let
+                                            // the requester know why his execution request is
+                                            // not accepted. If the session is removed just
+                                            // after the time out, then whe the user request to
+                                            // continue the execution he will recieved an
+                                            // invalid session error and not a time out error.
+                                            if (System.currentTimeMillis() - creationStamp > SESSION_TIMEOUT * 1000 * 2) {
+                                                // Remove the expired session
+                                                executingCommands.remove(sessionId);
+                                            }
+                                        }
+                                    }
+                                    try {
+                                        Thread.sleep(1000);
+                                    }
+                                    catch (InterruptedException ie) {
+                                        // Ignore.
+                                    }
+                                }
+                            }
+
+                        });
+                        sessionsSweeper.setDaemon(true);
+                        sessionsSweeper.start();
+                    }
+                }
+
+                // Sends the response packet
+                connection.sendPacket(response);
+
+            }
+            catch (XMPPException e) {
+                // If there is an exception caused by the next, complete,
+                // prev or cancel method, then that error is returned to the
+                // requester.
+                XMPPError error = e.getXMPPError();
+
+                // If the error type is cancel, then the execution is
+                // canceled therefore the status must show that, and the
+                // command be removed from the executing list.
+                if (XMPPError.Type.CANCEL.equals(error.getType())) {
+                    response.setStatus(Status.canceled);
+                    executingCommands.remove(sessionId);
+                }
+                respondError(response, error);
+                e.printStackTrace();
+            }
+        }
+        else {
+            LocalCommand command = executingCommands.get(sessionId);
+
+            // Check that a command exists for the specified sessionID
+            // This also handles if the command was removed in the meanwhile
+            // of getting the key and the value of the map.
+            if (command == null) {
+                respondError(response, XMPPError.Condition.bad_request,
+                        AdHocCommand.SpecificErrorCondition.badSessionid);
+                return;
+            }
+
+            // Check if the Session data has expired (default is 10 minutes)
+            long creationStamp = command.getCreationDate();
+            if (System.currentTimeMillis() - creationStamp > SESSION_TIMEOUT * 1000) {
+                // Remove the expired session
+                executingCommands.remove(sessionId);
+
+                // Answer a not_allowed error (session-expired)
+                respondError(response, XMPPError.Condition.not_allowed,
+                        AdHocCommand.SpecificErrorCondition.sessionExpired);
+                return;
+            }
+
+            /*
+             * Since the requester could send two requests for the same
+             * executing command i.e. the same session id, all the execution of
+             * the action must be synchronized to avoid inconsistencies.
+             */
+            synchronized (command) {
+                Action action = requestData.getAction();
+
+                // If the action is unknown the respond an error
+                if (action != null && action.equals(Action.unknown)) {
+                    respondError(response, XMPPError.Condition.bad_request,
+                            AdHocCommand.SpecificErrorCondition.malformedAction);
+                    return;
+                }
+
+                // If the user didn't specify an action or specify the execute
+                // action then follow the actual default execute action
+                if (action == null || Action.execute.equals(action)) {
+                    action = command.getExecuteAction();
+                }
+
+                // Check that the specified action was previously
+                // offered
+                if (!command.isValidAction(action)) {
+                    respondError(response, XMPPError.Condition.bad_request,
+                            AdHocCommand.SpecificErrorCondition.badAction);
+                    return;
+                }
+
+                try {
+                    // TODO: Check that all the requierd fields of the form are
+                    // TODO: filled, if not throw an exception. This will simplify the
+                    // TODO: construction of new commands
+
+                    // Since all errors were passed, the response is now a
+                    // result
+                    response.setType(IQ.Type.RESULT);
+
+                    // Set the new data to the command.
+                    command.setData(response);
+
+                    if (Action.next.equals(action)) {
+                        command.incrementStage();
+                        command.next(new Form(requestData.getForm()));
+                        if (command.isLastStage()) {
+                            // If it is the last stage then the command is
+                            // completed
+                            response.setStatus(Status.completed);
+                        }
+                        else {
+                            // Otherwise it is still executing
+                            response.setStatus(Status.executing);
+                        }
+                    }
+                    else if (Action.complete.equals(action)) {
+                        command.incrementStage();
+                        command.complete(new Form(requestData.getForm()));
+                        response.setStatus(Status.completed);
+                        // Remove the completed session
+                        executingCommands.remove(sessionId);
+                    }
+                    else if (Action.prev.equals(action)) {
+                        command.decrementStage();
+                        command.prev();
+                    }
+                    else if (Action.cancel.equals(action)) {
+                        command.cancel();
+                        response.setStatus(Status.canceled);
+                        // Remove the canceled session
+                        executingCommands.remove(sessionId);
+                    }
+
+                    connection.sendPacket(response);
+                }
+                catch (XMPPException e) {
+                    // If there is an exception caused by the next, complete,
+                    // prev or cancel method, then that error is returned to the
+                    // requester.
+                    XMPPError error = e.getXMPPError();
+
+                    // If the error type is cancel, then the execution is
+                    // canceled therefore the status must show that, and the
+                    // command be removed from the executing list.
+                    if (XMPPError.Type.CANCEL.equals(error.getType())) {
+                        response.setStatus(Status.canceled);
+                        executingCommands.remove(sessionId);
+                    }
+                    respondError(response, error);
+
+                    e.printStackTrace();
+                }
+            }
+        }
+    }
+
+    /**
+     * Responds an error with an specific condition.
+     * 
+     * @param response the response to send.
+     * @param condition the condition of the error.
+     */
+    private void respondError(AdHocCommandData response,
+            XMPPError.Condition condition) {
+        respondError(response, new XMPPError(condition));
+    }
+
+    /**
+     * Responds an error with an specific condition.
+     * 
+     * @param response the response to send.
+     * @param condition the condition of the error.
+     * @param specificCondition the adhoc command error condition.
+     */
+    private void respondError(AdHocCommandData response, XMPPError.Condition condition,
+            AdHocCommand.SpecificErrorCondition specificCondition)
+    {
+        XMPPError error = new XMPPError(condition);
+        error.addExtension(new AdHocCommandData.SpecificError(specificCondition));
+        respondError(response, error);
+    }
+
+    /**
+     * Responds an error with an specific error.
+     * 
+     * @param response the response to send.
+     * @param error the error to send.
+     */
+    private void respondError(AdHocCommandData response, XMPPError error) {
+        response.setType(IQ.Type.ERROR);
+        response.setError(error);
+        connection.sendPacket(response);
+    }
+
+    /**
+     * Creates a new instance of a command to be used by a new execution request
+     * 
+     * @param commandNode the command node that identifies it.
+     * @param sessionID the session id of this execution.
+     * @return the command instance to execute.
+     * @throws XMPPException if there is problem creating the new instance.
+     */
+    private LocalCommand newInstanceOfCmd(String commandNode, String sessionID)
+            throws XMPPException
+    {
+        AdHocCommandInfo commandInfo = commands.get(commandNode);
+        LocalCommand command;
+        try {
+            command = (LocalCommand) commandInfo.getCommandInstance();
+            command.setSessionID(sessionID);
+            command.setName(commandInfo.getName());
+            command.setNode(commandInfo.getNode());
+        }
+        catch (InstantiationException e) {
+            e.printStackTrace();
+            throw new XMPPException(new XMPPError(
+                    XMPPError.Condition.interna_server_error));
+        }
+        catch (IllegalAccessException e) {
+            e.printStackTrace();
+            throw new XMPPException(new XMPPError(
+                    XMPPError.Condition.interna_server_error));
+        }
+        return command;
+    }
+
+    /**
+     * Returns the registered commands of this command manager, which is related
+     * to a connection.
+     * 
+     * @return the registered commands.
+     */
+    private Collection<AdHocCommandInfo> getRegisteredCommands() {
+        return commands.values();
+    }
+
+    /**
+     * Stores ad-hoc command information.
+     */
+    private static class AdHocCommandInfo {
+
+        private String node;
+        private String name;
+        private String ownerJID;
+        private LocalCommandFactory factory;
+
+        public AdHocCommandInfo(String node, String name, String ownerJID,
+                LocalCommandFactory factory)
+        {
+            this.node = node;
+            this.name = name;
+            this.ownerJID = ownerJID;
+            this.factory = factory;
+        }
+
+        public LocalCommand getCommandInstance() throws InstantiationException,
+                IllegalAccessException
+        {
+            return factory.getInstance();
+        }
+
+        public String getName() {
+            return name;
+        }
+
+        public String getNode() {
+            return node;
+        }
+
+        public String getOwnerJID() {
+            return ownerJID;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/commands/AdHocCommandNote.java b/src/org/jivesoftware/smackx/commands/AdHocCommandNote.java
new file mode 100755
index 0000000..10dedbe
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/AdHocCommandNote.java
@@ -0,0 +1,86 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.commands;
+
+/**
+ * Notes can be added to a command execution response. A note has a type and value.
+ * 
+ * @author Gabriel Guardincerri
+ */
+public class AdHocCommandNote {
+
+    private Type type;
+    private String value;
+
+    /**
+     * Creates a new adhoc command note with the specified type and value.
+     *
+     * @param type the type of the note.
+     * @param value the value of the note.
+     */
+    public AdHocCommandNote(Type type, String value) {
+        this.type = type;
+        this.value = value;
+    }
+
+    /**
+     * Returns the value or message of the note.
+     * 
+     * @return the value or message of the note.
+     */
+    public String getValue() {
+        return value;
+    }
+
+    /**
+     * Return the type of the note.
+     * 
+     * @return the type of the note.
+     */
+    public Type getType() {
+        return type;
+    }
+
+    /**
+     * Represents a note type.
+     */
+    public enum Type {
+
+        /**
+         * The note is informational only. This is not really an exceptional
+         * condition.
+         */
+        info,
+
+        /**
+         * The note indicates a warning. Possibly due to illogical (yet valid)
+         * data.
+         */
+        warn,
+
+        /**
+         * The note indicates an error. The text should indicate the reason for
+         * the error.
+         */
+        error
+    }
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/commands/LocalCommand.java b/src/org/jivesoftware/smackx/commands/LocalCommand.java
new file mode 100755
index 0000000..627d30e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/LocalCommand.java
@@ -0,0 +1,169 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.commands;
+
+import org.jivesoftware.smackx.packet.AdHocCommandData;
+
+/**
+ * Represents a command that can be executed locally from a remote location. This
+ * class must be extended to implement an specific ad-hoc command. This class
+ * provides some useful tools:<ul>
+ *      <li>Node</li>
+ *      <li>Name</li>
+ *      <li>Session ID</li>
+ *      <li>Current Stage</li>
+ *      <li>Available actions</li>
+ *      <li>Default action</li>
+ * </ul><p/>
+ * To implement a new command extend this class and implement all the abstract
+ * methods. When implementing the actions remember that they could be invoked
+ * several times, and that you must use the current stage number to know what to
+ * do.
+ * 
+ * @author Gabriel Guardincerri
+ */
+public abstract class LocalCommand extends AdHocCommand {
+
+    /**
+     * The time stamp of first invokation of the command. Used to implement the session timeout.
+     */
+    private long creationDate;
+
+    /**
+     * The unique ID of the execution of the command.
+     */
+    private String sessionID;
+
+    /**
+     * The full JID of the host of the command.
+     */
+    private String ownerJID;
+
+    /**
+     * The number of the current stage.
+     */
+    private int currenStage;
+
+    public LocalCommand() {
+        super();
+        this.creationDate = System.currentTimeMillis();
+        currenStage = -1;
+    }
+
+    /**
+     * The sessionID is an unique identifier of an execution request. This is
+     * automatically handled and should not be called.
+     * 
+     * @param sessionID the unique session id of this execution
+     */
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+        getData().setSessionID(sessionID);
+    }
+
+    /**
+     * Returns the session ID of this execution.
+     * 
+     * @return the unique session id of this execution
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    /**
+     * Sets the JID of the command host. This is automatically handled and should
+     * not be called.
+     * 
+     * @param ownerJID the JID of the owner.
+     */
+    public void setOwnerJID(String ownerJID) {
+        this.ownerJID = ownerJID;
+    }
+
+    @Override
+    public String getOwnerJID() {
+        return ownerJID;
+    }
+
+    /**
+     * Returns the date the command was created.
+     * 
+     * @return the date the command was created.
+     */
+    public long getCreationDate() {
+        return creationDate;
+    }
+
+    /**
+     * Returns true if the current stage is the last one. If it is then the
+     * execution of some action will complete the execution of the command.
+     * Commands that don't have multiple stages can always return <tt>true</tt>.
+     * 
+     * @return true if the command is in the last stage.
+     */
+    public abstract boolean isLastStage();
+
+    /**
+     * Returns true if the specified requester has permission to execute all the
+     * stages of this action. This is checked when the first request is received,
+     * if the permission is grant then the requester will be able to execute
+     * all the stages of the command. It is not checked again during the
+     * execution.
+     *
+     * @param jid the JID to check permissions on.
+     * @return true if the user has permission to execute this action.
+     */
+    public abstract boolean hasPermission(String jid);
+
+    /**
+     * Returns the currently executing stage number. The first stage number is
+     * 0. During the execution of the first action this method will answer 0.
+     *
+     * @return the current stage number.
+     */
+    public int getCurrentStage() {
+        return currenStage;
+    }
+
+    @Override
+    void setData(AdHocCommandData data) {
+        data.setSessionID(sessionID);
+        super.setData(data);
+    }
+
+    /**
+     * Increase the current stage number. This is automatically handled and should
+     * not be called.
+     * 
+     */
+    void incrementStage() {
+        currenStage++;
+    }
+
+    /**
+     * Decrease the current stage number. This is automatically handled and should
+     * not be called.
+     * 
+     */
+    void decrementStage() {
+        currenStage--;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/commands/LocalCommandFactory.java b/src/org/jivesoftware/smackx/commands/LocalCommandFactory.java
new file mode 100644
index 0000000..83fc455
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/LocalCommandFactory.java
@@ -0,0 +1,43 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2008 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.commands;
+
+/**
+ * A factory for creating local commands. It's useful in cases where instantiation
+ * of a command is more complicated than just using the default constructor. For example,
+ * when arguments must be passed into the constructor or when using a dependency injection
+ * framework. When a LocalCommandFactory isn't used, you can provide the AdHocCommandManager
+ * a Class object instead. For more details, see
+ * {@link AdHocCommandManager#registerCommand(String, String, LocalCommandFactory)}. 
+ *
+ * @author Matt Tucker
+ */
+public interface LocalCommandFactory {
+
+    /**
+     * Returns an instance of a LocalCommand.
+     *
+     * @return a LocalCommand instance.
+     * @throws InstantiationException if creating an instance failed.
+     * @throws IllegalAccessException if creating an instance is not allowed.
+     */
+    public LocalCommand getInstance() throws InstantiationException, IllegalAccessException;
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/commands/RemoteCommand.java b/src/org/jivesoftware/smackx/commands/RemoteCommand.java
new file mode 100755
index 0000000..3c2df1d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/commands/RemoteCommand.java
@@ -0,0 +1,201 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.commands;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.packet.AdHocCommandData;
+
+/**
+ * Represents a command that is in a remote location. Invoking one of the
+ * {@link AdHocCommand.Action#execute execute}, {@link AdHocCommand.Action#next next},
+ * {@link AdHocCommand.Action#prev prev}, {@link AdHocCommand.Action#cancel cancel} or
+ * {@link AdHocCommand.Action#complete complete} actions results in executing that
+ * action in the remote location. In response to that action the internal state
+ * of the this command instance will change. For example, if the command is a
+ * single stage command, then invoking the execute action will execute this
+ * action in the remote location. After that the local instance will have a
+ * state of "completed" and a form or notes that applies.
+ *
+ * @author Gabriel Guardincerri
+ *
+ */
+public class RemoteCommand extends AdHocCommand {
+
+    /**
+     * The connection that is used to execute this command
+     */
+    private Connection connection;
+
+    /**
+     * The full JID of the command host
+     */
+    private String jid;
+
+    /**
+     * The session ID of this execution.
+     */
+    private String sessionID;
+
+
+    /**
+     * The number of milliseconds to wait for a response from the server
+     * The default value is the default packet reply timeout (5000 ms).
+     */
+    private long packetReplyTimeout;
+
+    /**
+     * Creates a new RemoteCommand that uses an specific connection to execute a
+     * command identified by <code>node</code> in the host identified by
+     * <code>jid</code>
+     *
+     * @param connection the connection to use for the execution.
+     * @param node the identifier of the command.
+     * @param jid the JID of the host.
+     */
+    protected RemoteCommand(Connection connection, String node, String jid) {
+        super();
+        this.connection = connection;
+        this.jid = jid;
+        this.setNode(node);
+        this.packetReplyTimeout = SmackConfiguration.getPacketReplyTimeout();
+    }
+
+    @Override
+    public void cancel() throws XMPPException {
+        executeAction(Action.cancel, packetReplyTimeout);
+    }
+
+    @Override
+    public void complete(Form form) throws XMPPException {
+        executeAction(Action.complete, form, packetReplyTimeout);
+    }
+
+    @Override
+    public void execute() throws XMPPException {
+        executeAction(Action.execute, packetReplyTimeout);
+    }
+
+    /**
+     * Executes the default action of the command with the information provided
+     * in the Form. This form must be the anwser form of the previous stage. If
+     * there is a problem executing the command it throws an XMPPException.
+     *
+     * @param form the form anwser of the previous stage.
+     * @throws XMPPException if an error occurs.
+     */
+    public void execute(Form form) throws XMPPException {
+        executeAction(Action.execute, form, packetReplyTimeout);
+    }
+
+    @Override
+    public void next(Form form) throws XMPPException {
+        executeAction(Action.next, form, packetReplyTimeout);
+    }
+
+    @Override
+    public void prev() throws XMPPException {
+        executeAction(Action.prev, packetReplyTimeout);
+    }
+
+    private void executeAction(Action action, long packetReplyTimeout) throws XMPPException {
+        executeAction(action, null, packetReplyTimeout);
+    }
+
+    /**
+     * Executes the <code>action</codo> with the <code>form</code>.
+     * The action could be any of the available actions. The form must
+     * be the anwser of the previous stage. It can be <tt>null</tt> if it is the first stage.
+     *
+     * @param action the action to execute.
+     * @param form the form with the information.
+     * @param timeout the amount of time to wait for a reply.
+     * @throws XMPPException if there is a problem executing the command.
+     */
+    private void executeAction(Action action, Form form, long timeout) throws XMPPException {
+        // TODO: Check that all the required fields of the form were filled, if
+        // TODO: not throw the corresponding exeption. This will make a faster response,
+        // TODO: since the request is stoped before it's sent.
+        AdHocCommandData data = new AdHocCommandData();
+        data.setType(IQ.Type.SET);
+        data.setTo(getOwnerJID());
+        data.setNode(getNode());
+        data.setSessionID(sessionID);
+        data.setAction(action);
+
+        if (form != null) {
+            data.setForm(form.getDataFormToSend());
+        }
+
+        PacketCollector collector = connection.createPacketCollector(
+                new PacketIDFilter(data.getPacketID()));
+
+        connection.sendPacket(data);
+
+        Packet response = collector.nextResult(timeout);
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+
+        AdHocCommandData responseData = (AdHocCommandData) response;
+        this.sessionID = responseData.getSessionID();
+        super.setData(responseData);
+    }
+
+    @Override
+    public String getOwnerJID() {
+        return jid;
+    }
+
+    /**
+     * Returns the number of milliseconds to wait for a respone. The
+     * {@link SmackConfiguration#getPacketReplyTimeout default} value
+     * should be adjusted for commands that can take a long time to execute.
+     *
+     * @return the number of milliseconds to wait for responses.
+     */
+    public long getPacketReplyTimeout() {
+        return packetReplyTimeout;
+    }
+
+    /**
+     * Returns the number of milliseconds to wait for a respone. The
+     * {@link SmackConfiguration#getPacketReplyTimeout default} value
+     * should be adjusted for commands that can take a long time to execute.
+     *
+     * @param packetReplyTimeout the number of milliseconds to wait for responses.
+     */
+    public void setPacketReplyTimeout(long packetReplyTimeout) {
+        this.packetReplyTimeout = packetReplyTimeout;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/debugger/package.html b/src/org/jivesoftware/smackx/debugger/package.html
new file mode 100644
index 0000000..8ea20e0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/debugger/package.html
@@ -0,0 +1 @@
+<body>Smack optional Debuggers.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/entitycaps/EntityCapsManager.java b/src/org/jivesoftware/smackx/entitycaps/EntityCapsManager.java
new file mode 100644
index 0000000..1da222e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/entitycaps/EntityCapsManager.java
@@ -0,0 +1,713 @@
+/**
+ * Copyright 2009 Jonas Ådahl.
+ * Copyright 2011-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.entitycaps;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketInterceptor;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPConnection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.filter.NotFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.util.Base64;
+import org.jivesoftware.smack.util.Cache;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.NodeInformationProvider;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.entitycaps.cache.EntityCapsPersistentCache;
+import org.jivesoftware.smackx.entitycaps.packet.CapsExtension;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Feature;
+import org.jivesoftware.smackx.packet.DiscoverInfo.Identity;
+import org.jivesoftware.smackx.packet.DiscoverItems.Item;
+
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Queue;
+import java.util.SortedSet;
+import java.util.TreeSet;
+import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.io.IOException;
+import java.lang.ref.WeakReference;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+
+/**
+ * Keeps track of entity capabilities.
+ * 
+ * @author Florian Schmaus
+ */
+public class EntityCapsManager {
+
+    public static final String NAMESPACE = "http://jabber.org/protocol/caps";
+    public static final String ELEMENT = "c";
+
+    private static final String ENTITY_NODE = "http://www.igniterealtime.org/projects/smack";
+    private static final Map<String, MessageDigest> SUPPORTED_HASHES = new HashMap<String, MessageDigest>();
+
+    protected static EntityCapsPersistentCache persistentCache;
+
+    private static Map<Connection, EntityCapsManager> instances = Collections
+            .synchronizedMap(new WeakHashMap<Connection, EntityCapsManager>());
+
+    /**
+     * Map of (node + '#" + hash algorithm) to DiscoverInfo data
+     */
+    protected static Map<String, DiscoverInfo> caps = new Cache<String, DiscoverInfo>(1000, -1);
+
+    /**
+     * Map of Full JID -&gt; DiscoverInfo/null. In case of c2s connection the
+     * key is formed as user@server/resource (resource is required) In case of
+     * link-local connection the key is formed as user@host (no resource) In
+     * case of a server or component the key is formed as domain
+     */
+    protected static Map<String, NodeVerHash> jidCaps = new Cache<String, NodeVerHash>(10000, -1);
+
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                if (connection instanceof XMPPConnection)
+                    new EntityCapsManager(connection);
+            }
+        });
+
+        try {
+            MessageDigest sha1MessageDigest = MessageDigest.getInstance("SHA-1");
+            SUPPORTED_HASHES.put("sha-1", sha1MessageDigest);
+        } catch (NoSuchAlgorithmException e) {
+            // Ignore
+        }
+    }
+
+    private WeakReference<Connection> weakRefConnection;
+    private ServiceDiscoveryManager sdm;
+    private boolean entityCapsEnabled;
+    private String currentCapsVersion;
+    private boolean presenceSend = false;
+    private Queue<String> lastLocalCapsVersions = new ConcurrentLinkedQueue<String>();
+
+    /**
+     * Add DiscoverInfo to the database.
+     * 
+     * @param nodeVer
+     *            The node and verification String (e.g.
+     *            "http://psi-im.org#q07IKJEyjvHSyhy//CH0CxmKi8w=").
+     * @param info
+     *            DiscoverInfo for the specified node.
+     */
+    public static void addDiscoverInfoByNode(String nodeVer, DiscoverInfo info) {
+        caps.put(nodeVer, info);
+
+        if (persistentCache != null)
+            persistentCache.addDiscoverInfoByNodePersistent(nodeVer, info);
+    }
+
+    /**
+     * Get the Node version (node#ver) of a JID. Returns a String or null if
+     * EntiyCapsManager does not have any information.
+     * 
+     * @param user
+     *            the user (Full JID)
+     * @return the node version (node#ver) or null
+     */
+    public static String getNodeVersionByJid(String jid) {
+        NodeVerHash nvh = jidCaps.get(jid);
+        if (nvh != null) {
+            return nvh.nodeVer;
+        } else {
+            return null;
+        }
+    }
+
+    public static NodeVerHash getNodeVerHashByJid(String jid) {
+        return jidCaps.get(jid);
+    }
+
+    /**
+     * Get the discover info given a user name. The discover info is returned if
+     * the user has a node#ver associated with it and the node#ver has a
+     * discover info associated with it.
+     * 
+     * @param user
+     *            user name (Full JID)
+     * @return the discovered info
+     */
+    public static DiscoverInfo getDiscoverInfoByUser(String user) {
+        NodeVerHash nvh = jidCaps.get(user);
+        if (nvh == null)
+            return null;
+
+        return getDiscoveryInfoByNodeVer(nvh.nodeVer);
+    }
+
+    /**
+     * Retrieve DiscoverInfo for a specific node.
+     * 
+     * @param nodeVer
+     *            The node name (e.g.
+     *            "http://psi-im.org#q07IKJEyjvHSyhy//CH0CxmKi8w=").
+     * @return The corresponding DiscoverInfo or null if none is known.
+     */
+    public static DiscoverInfo getDiscoveryInfoByNodeVer(String nodeVer) {
+        DiscoverInfo info = caps.get(nodeVer);
+        if (info != null)
+            info = new DiscoverInfo(info);
+
+        return info;
+    }
+
+    /**
+     * Set the persistent cache implementation
+     * 
+     * @param cache
+     * @throws IOException
+     */
+    public static void setPersistentCache(EntityCapsPersistentCache cache) throws IOException {
+        if (persistentCache != null)
+            throw new IllegalStateException("Entity Caps Persistent Cache was already set");
+        persistentCache = cache;
+        persistentCache.replay();
+    }
+
+    /**
+     * Sets the maximum Cache size for the JID to nodeVer Cache
+     * 
+     * @param maxCacheSize
+     */
+    @SuppressWarnings("rawtypes")
+    public static void setJidCapsMaxCacheSize(int maxCacheSize) {
+        ((Cache) jidCaps).setMaxCacheSize(maxCacheSize);
+    }
+
+    /**
+     * Sets the maximum Cache size for the nodeVer to DiscoverInfo Cache
+     * 
+     * @param maxCacheSize
+     */
+    @SuppressWarnings("rawtypes")
+    public static void setCapsMaxCacheSize(int maxCacheSize) {
+        ((Cache) caps).setMaxCacheSize(maxCacheSize);
+    }
+
+    private EntityCapsManager(Connection connection) {
+        this.weakRefConnection = new WeakReference<Connection>(connection);
+        this.sdm = ServiceDiscoveryManager.getInstanceFor(connection);
+        init();
+    }
+
+    private void init() {
+        Connection connection = weakRefConnection.get();
+        instances.put(connection, this);
+
+        connection.addConnectionListener(new ConnectionListener() {
+            public void connectionClosed() {
+                // Unregister this instance since the connection has been closed
+                presenceSend = false;
+                instances.remove(weakRefConnection.get());
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                presenceSend = false;
+            }
+
+            public void reconnectionFailed(Exception e) {
+                // ignore
+            }
+
+            public void reconnectingIn(int seconds) {
+                // ignore
+            }
+
+            public void reconnectionSuccessful() {
+                // ignore
+            }
+        });
+
+        // This calculates the local entity caps version
+        updateLocalEntityCaps();
+
+        if (SmackConfiguration.autoEnableEntityCaps())
+            enableEntityCaps();
+
+        PacketFilter packetFilter = new AndFilter(new PacketTypeFilter(Presence.class), new PacketExtensionFilter(
+                ELEMENT, NAMESPACE));
+        connection.addPacketListener(new PacketListener() {
+            // Listen for remote presence stanzas with the caps extension
+            // If we receive such a stanza, record the JID and nodeVer
+            @Override
+            public void processPacket(Packet packet) {
+                if (!entityCapsEnabled())
+                    return;
+
+                CapsExtension ext = (CapsExtension) packet.getExtension(EntityCapsManager.ELEMENT,
+                        EntityCapsManager.NAMESPACE);
+
+                String hash = ext.getHash().toLowerCase();
+                if (!SUPPORTED_HASHES.containsKey(hash))
+                    return;
+
+                String from = packet.getFrom();
+                String node = ext.getNode();
+                String ver = ext.getVer();
+
+                jidCaps.put(from, new NodeVerHash(node, ver, hash));
+            }
+
+        }, packetFilter);
+
+        packetFilter = new AndFilter(new PacketTypeFilter(Presence.class), new NotFilter(new PacketExtensionFilter(
+                ELEMENT, NAMESPACE)));
+        connection.addPacketListener(new PacketListener() {
+            @Override
+            public void processPacket(Packet packet) {
+                // always remove the JID from the map, even if entityCaps are
+                // disabled
+                String from = packet.getFrom();
+                jidCaps.remove(from);
+            }
+        }, packetFilter);
+
+        packetFilter = new PacketTypeFilter(Presence.class);
+        connection.addPacketSendingListener(new PacketListener() {
+            @Override
+            public void processPacket(Packet packet) {
+                presenceSend = true;
+            }
+        }, packetFilter);
+
+        // Intercept presence packages and add caps data when intended.
+        // XEP-0115 specifies that a client SHOULD include entity capabilities
+        // with every presence notification it sends.
+        PacketFilter capsPacketFilter = new PacketTypeFilter(Presence.class);
+        PacketInterceptor packetInterceptor = new PacketInterceptor() {
+            public void interceptPacket(Packet packet) {
+                if (!entityCapsEnabled)
+                    return;
+
+                CapsExtension caps = new CapsExtension(ENTITY_NODE, getCapsVersion(), "sha-1");
+                packet.addExtension(caps);
+            }
+        };
+        connection.addPacketInterceptor(packetInterceptor, capsPacketFilter);
+        // It's important to do this as last action. Since it changes the
+        // behavior of the SDM in some ways
+        sdm.setEntityCapsManager(this);
+    }
+
+    public static synchronized EntityCapsManager getInstanceFor(Connection connection) {
+        // For testing purposed forbid EntityCaps for non XMPPConnections
+        // it may work on BOSH connections too
+        if (!(connection instanceof XMPPConnection))
+            return null;
+
+        if (SUPPORTED_HASHES.size() <= 0)
+            return null;
+
+        EntityCapsManager entityCapsManager = instances.get(connection);
+
+        if (entityCapsManager == null) {
+            entityCapsManager = new EntityCapsManager(connection);
+        }
+
+        return entityCapsManager;
+    }
+
+    public void enableEntityCaps() {
+        // Add Entity Capabilities (XEP-0115) feature node.
+        sdm.addFeature(NAMESPACE);
+        updateLocalEntityCaps();
+        entityCapsEnabled = true;
+    }
+
+    public void disableEntityCaps() {
+        entityCapsEnabled = false;
+        sdm.removeFeature(NAMESPACE);
+    }
+
+    public boolean entityCapsEnabled() {
+        return entityCapsEnabled;
+    }
+
+    /**
+     * Remove a record telling what entity caps node a user has.
+     * 
+     * @param user
+     *            the user (Full JID)
+     */
+    public void removeUserCapsNode(String user) {
+        jidCaps.remove(user);
+    }
+
+    /**
+     * Get our own caps version. The version depends on the enabled features. A
+     * caps version looks like '66/0NaeaBKkwk85efJTGmU47vXI='
+     * 
+     * @return our own caps version
+     */
+    public String getCapsVersion() {
+        return currentCapsVersion;
+    }
+
+    /**
+     * Returns the local entity's NodeVer (e.g.
+     * "http://www.igniterealtime.org/projects/smack/#66/0NaeaBKkwk85efJTGmU47vXI=
+     * )
+     * 
+     * @return
+     */
+    public String getLocalNodeVer() {
+        return ENTITY_NODE + '#' + getCapsVersion();
+    }
+
+    /**
+     * Returns true if Entity Caps are supported by a given JID
+     * 
+     * @param jid
+     * @return
+     */
+    public boolean areEntityCapsSupported(String jid) {
+        if (jid == null)
+            return false;
+
+        try {
+            DiscoverInfo result = sdm.discoverInfo(jid);
+            return result.containsFeature(NAMESPACE);
+        } catch (XMPPException e) {
+            return false;
+        }
+    }
+
+    /**
+     * Returns true if Entity Caps are supported by the local service/server
+     * 
+     * @return
+     */
+    public boolean areEntityCapsSupportedByServer() {
+        return areEntityCapsSupported(weakRefConnection.get().getServiceName());
+    }
+
+    /**
+     * Updates the local user Entity Caps information with the data provided
+     * 
+     * If we are connected and there was already a presence send, another
+     * presence is send to inform others about your new Entity Caps node string.
+     * 
+     * @param discoverInfo
+     *            the local users discover info (mostly the service discovery
+     *            features)
+     * @param identityType
+     *            the local users identity type
+     * @param identityName
+     *            the local users identity name
+     * @param extendedInfo
+     *            the local users extended info
+     */
+    public void updateLocalEntityCaps() {
+        Connection connection = weakRefConnection.get();
+
+        DiscoverInfo discoverInfo = new DiscoverInfo();
+        discoverInfo.setType(IQ.Type.RESULT);
+        discoverInfo.setNode(getLocalNodeVer());
+        if (connection != null)
+            discoverInfo.setFrom(connection.getUser());
+        sdm.addDiscoverInfoTo(discoverInfo);
+
+        currentCapsVersion = generateVerificationString(discoverInfo, "sha-1");
+        addDiscoverInfoByNode(ENTITY_NODE + '#' + currentCapsVersion, discoverInfo);
+        if (lastLocalCapsVersions.size() > 10) {
+            String oldCapsVersion = lastLocalCapsVersions.poll();
+            sdm.removeNodeInformationProvider(ENTITY_NODE + '#' + oldCapsVersion);
+        }
+        lastLocalCapsVersions.add(currentCapsVersion);
+
+        caps.put(currentCapsVersion, discoverInfo);
+        if (connection != null)
+            jidCaps.put(connection.getUser(), new NodeVerHash(ENTITY_NODE, currentCapsVersion, "sha-1"));
+
+        sdm.setNodeInformationProvider(ENTITY_NODE + '#' + currentCapsVersion, new NodeInformationProvider() {
+            List<String> features = sdm.getFeaturesList();
+            List<Identity> identities = new LinkedList<Identity>(ServiceDiscoveryManager.getIdentities());
+            List<PacketExtension> packetExtensions = sdm.getExtendedInfoAsList();
+
+            @Override
+            public List<Item> getNodeItems() {
+                return null;
+            }
+
+            @Override
+            public List<String> getNodeFeatures() {
+                return features;
+            }
+
+            @Override
+            public List<Identity> getNodeIdentities() {
+                return identities;
+            }
+
+            @Override
+            public List<PacketExtension> getNodePacketExtensions() {
+                return packetExtensions;
+            }
+        });
+
+        // Send an empty presence, and let the packet intercepter
+        // add a <c/> node to it.
+        // See http://xmpp.org/extensions/xep-0115.html#advertise
+        // We only send a presence packet if there was already one send
+        // to respect ConnectionConfiguration.isSendPresence()
+        if (connection != null && connection.isAuthenticated() && presenceSend) {
+            Presence presence = new Presence(Presence.Type.available);
+            connection.sendPacket(presence);
+        }
+    }
+
+    /**
+     * Verify DisoverInfo and Caps Node as defined in XEP-0115 5.4 Processing
+     * Method
+     * 
+     * @see <a href="http://xmpp.org/extensions/xep-0115.html#ver-proc">XEP-0115
+     *      5.4 Processing Method</a>
+     * 
+     * @param capsNode
+     *            the caps node (i.e. node#ver)
+     * @param info
+     * @return true if it's valid and should be cache, false if not
+     */
+    public static boolean verifyDiscoverInfoVersion(String ver, String hash, DiscoverInfo info) {
+        // step 3.3 check for duplicate identities
+        if (info.containsDuplicateIdentities())
+            return false;
+
+        // step 3.4 check for duplicate features
+        if (info.containsDuplicateFeatures())
+            return false;
+
+        // step 3.5 check for well-formed packet extensions
+        if (verifyPacketExtensions(info))
+            return false;
+
+        String calculatedVer = generateVerificationString(info, hash);
+
+        if (!ver.equals(calculatedVer))
+            return false;
+
+        return true;
+    }
+
+    /**
+     * 
+     * @param info
+     * @return true if the packet extensions is ill-formed
+     */
+    protected static boolean verifyPacketExtensions(DiscoverInfo info) {
+        List<FormField> foundFormTypes = new LinkedList<FormField>();
+        for (Iterator<PacketExtension> i = info.getExtensions().iterator(); i.hasNext();) {
+            PacketExtension pe = i.next();
+            if (pe.getNamespace().equals(Form.NAMESPACE)) {
+                DataForm df = (DataForm) pe;
+                for (Iterator<FormField> it = df.getFields(); it.hasNext();) {
+                    FormField f = it.next();
+                    if (f.getVariable().equals("FORM_TYPE")) {
+                        for (FormField fft : foundFormTypes) {
+                            if (f.equals(fft))
+                                return true;
+                        }
+                        foundFormTypes.add(f);
+                    }
+                }
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Generates a XEP-115 Verification String
+     * 
+     * @see <a href="http://xmpp.org/extensions/xep-0115.html#ver">XEP-115
+     *      Verification String</a>
+     * 
+     * @param discoverInfo
+     * @param hash
+     *            the used hash function
+     * @return The generated verification String or null if the hash is not
+     *         supported
+     */
+    protected static String generateVerificationString(DiscoverInfo discoverInfo, String hash) {
+        MessageDigest md = SUPPORTED_HASHES.get(hash.toLowerCase());
+        if (md == null)
+            return null;
+
+        DataForm extendedInfo = (DataForm) discoverInfo.getExtension(Form.ELEMENT, Form.NAMESPACE);
+
+        // 1. Initialize an empty string S ('sb' in this method).
+        StringBuilder sb = new StringBuilder(); // Use StringBuilder as we don't
+                                                // need thread-safe StringBuffer
+
+        // 2. Sort the service discovery identities by category and then by
+        // type and then by xml:lang
+        // (if it exists), formatted as CATEGORY '/' [TYPE] '/' [LANG] '/'
+        // [NAME]. Note that each slash is included even if the LANG or
+        // NAME is not included (in accordance with XEP-0030, the category and
+        // type MUST be included.
+        SortedSet<DiscoverInfo.Identity> sortedIdentities = new TreeSet<DiscoverInfo.Identity>();
+
+        for (Iterator<DiscoverInfo.Identity> it = discoverInfo.getIdentities(); it.hasNext();)
+            sortedIdentities.add(it.next());
+
+        // 3. For each identity, append the 'category/type/lang/name' to S,
+        // followed by the '<' character.
+        for (Iterator<DiscoverInfo.Identity> it = sortedIdentities.iterator(); it.hasNext();) {
+            DiscoverInfo.Identity identity = it.next();
+            sb.append(identity.getCategory());
+            sb.append("/");
+            sb.append(identity.getType());
+            sb.append("/");
+            sb.append(identity.getLanguage() == null ? "" : identity.getLanguage());
+            sb.append("/");
+            sb.append(identity.getName() == null ? "" : identity.getName());
+            sb.append("<");
+        }
+
+        // 4. Sort the supported service discovery features.
+        SortedSet<String> features = new TreeSet<String>();
+        for (Iterator<Feature> it = discoverInfo.getFeatures(); it.hasNext();)
+            features.add(it.next().getVar());
+
+        // 5. For each feature, append the feature to S, followed by the '<'
+        // character
+        for (String f : features) {
+            sb.append(f);
+            sb.append("<");
+        }
+
+        // only use the data form for calculation is it has a hidden FORM_TYPE
+        // field
+        // see XEP-0115 5.4 step 3.6
+        if (extendedInfo != null && extendedInfo.hasHiddenFormTypeField()) {
+            synchronized (extendedInfo) {
+                // 6. If the service discovery information response includes
+                // XEP-0128 data forms, sort the forms by the FORM_TYPE (i.e.,
+                // by the XML character data of the <value/> element).
+                SortedSet<FormField> fs = new TreeSet<FormField>(new Comparator<FormField>() {
+                    public int compare(FormField f1, FormField f2) {
+                        return f1.getVariable().compareTo(f2.getVariable());
+                    }
+                });
+
+                FormField ft = null;
+
+                for (Iterator<FormField> i = extendedInfo.getFields(); i.hasNext();) {
+                    FormField f = i.next();
+                    if (!f.getVariable().equals("FORM_TYPE")) {
+                        fs.add(f);
+                    } else {
+                        ft = f;
+                    }
+                }
+
+                // Add FORM_TYPE values
+                if (ft != null) {
+                    formFieldValuesToCaps(ft.getValues(), sb);
+                }
+
+                // 7. 3. For each field other than FORM_TYPE:
+                // 1. Append the value of the "var" attribute, followed by the
+                // '<' character.
+                // 2. Sort values by the XML character data of the <value/>
+                // element.
+                // 3. For each <value/> element, append the XML character data,
+                // followed by the '<' character.
+                for (FormField f : fs) {
+                    sb.append(f.getVariable());
+                    sb.append("<");
+                    formFieldValuesToCaps(f.getValues(), sb);
+                }
+            }
+        }
+        // 8. Ensure that S is encoded according to the UTF-8 encoding (RFC
+        // 3269).
+        // 9. Compute the verification string by hashing S using the algorithm
+        // specified in the 'hash' attribute (e.g., SHA-1 as defined in RFC
+        // 3174).
+        // The hashed data MUST be generated with binary output and
+        // encoded using Base64 as specified in Section 4 of RFC 4648
+        // (note: the Base64 output MUST NOT include whitespace and MUST set
+        // padding bits to zero).
+        byte[] digest = md.digest(sb.toString().getBytes());
+        return Base64.encodeBytes(digest);
+    }
+
+    private static void formFieldValuesToCaps(Iterator<String> i, StringBuilder sb) {
+        SortedSet<String> fvs = new TreeSet<String>();
+        while (i.hasNext()) {
+            fvs.add(i.next());
+        }
+        for (String fv : fvs) {
+            sb.append(fv);
+            sb.append("<");
+        }
+    }
+
+    public static class NodeVerHash {
+        private String node;
+        private String hash;
+        private String ver;
+        private String nodeVer;
+
+        NodeVerHash(String node, String ver, String hash) {
+            this.node = node;
+            this.ver = ver;
+            this.hash = hash;
+            nodeVer = node + "#" + ver;
+        }
+
+        public String getNodeVer() {
+            return nodeVer;
+        }
+
+        public String getNode() {
+            return node;
+        }
+
+        public String getHash() {
+            return hash;
+        }
+
+        public String getVer() {
+            return ver;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/entitycaps/cache/EntityCapsPersistentCache.java b/src/org/jivesoftware/smackx/entitycaps/cache/EntityCapsPersistentCache.java
new file mode 100644
index 0000000..0441043
--- /dev/null
+++ b/src/org/jivesoftware/smackx/entitycaps/cache/EntityCapsPersistentCache.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.entitycaps.cache;
+
+import java.io.IOException;
+
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+
+public interface EntityCapsPersistentCache {
+    /**
+     * Add an DiscoverInfo to the persistent Cache
+     * 
+     * @param node
+     * @param info
+     */
+    void addDiscoverInfoByNodePersistent(String node, DiscoverInfo info);
+
+    /**
+     * Replay the Caches data into EntityCapsManager
+     */
+    void replay() throws IOException;
+
+    /**
+     * Empty the Cache
+     */
+    void emptyCache();
+}
diff --git a/src/org/jivesoftware/smackx/entitycaps/cache/SimpleDirectoryPersistentCache.java b/src/org/jivesoftware/smackx/entitycaps/cache/SimpleDirectoryPersistentCache.java
new file mode 100644
index 0000000..0312c7e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/entitycaps/cache/SimpleDirectoryPersistentCache.java
@@ -0,0 +1,194 @@
+/**
+ *  Copyright 2011 Florian Schmaus
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.jivesoftware.smackx.entitycaps.cache;
+
+import java.io.DataInputStream;
+import java.io.DataOutputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.Reader;
+import java.io.StringReader;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.Base32Encoder;
+import org.jivesoftware.smack.util.Base64Encoder;
+import org.jivesoftware.smack.util.StringEncoder;
+import org.jivesoftware.smackx.entitycaps.EntityCapsManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.provider.DiscoverInfoProvider;
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+/**
+ * Simple implementation of an EntityCapsPersistentCache that uses a directory
+ * to store the Caps information for every known node. Every node is represented
+ * by an file.
+ * 
+ * @author Florian Schmaus
+ * 
+ */
+public class SimpleDirectoryPersistentCache implements EntityCapsPersistentCache {
+
+    private File cacheDir;
+    private StringEncoder filenameEncoder;
+
+    /**
+     * Creates a new SimpleDirectoryPersistentCache Object. Make sure that the
+     * cacheDir exists and that it's an directory.
+     * <p>
+     * Default filename encoder {@link Base32Encoder}, as this will work on all 
+     * filesystems, both case sensitive and case insensitive.  It does however 
+     * produce longer filenames.
+     * 
+     * @param cacheDir
+     */
+    public SimpleDirectoryPersistentCache(File cacheDir) {
+        this(cacheDir, Base32Encoder.getInstance());
+    }
+
+    /**
+     * Creates a new SimpleDirectoryPersistentCache Object. Make sure that the
+     * cacheDir exists and that it's an directory.
+     * 
+     * If your cacheDir is case insensitive then make sure to set the
+     * StringEncoder to {@link Base32Encoder} (which is the default).
+     * 
+     * @param cacheDir The directory where the cache will be stored.
+     * @param filenameEncoder Encodes the node string into a filename.
+     */
+    public SimpleDirectoryPersistentCache(File cacheDir, StringEncoder filenameEncoder) {
+        if (!cacheDir.exists())
+            throw new IllegalStateException("Cache directory \"" + cacheDir + "\" does not exist");
+        if (!cacheDir.isDirectory())
+            throw new IllegalStateException("Cache directory \"" + cacheDir + "\" is not a directory");
+
+        this.cacheDir = cacheDir;
+        this.filenameEncoder = filenameEncoder;
+    }
+
+    @Override
+    public void addDiscoverInfoByNodePersistent(String node, DiscoverInfo info) {
+        String filename = filenameEncoder.encode(node);
+        File nodeFile = new File(cacheDir, filename);
+        try {
+            if (nodeFile.createNewFile())
+                writeInfoToFile(nodeFile, info);
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+    }
+
+    @Override
+    public void replay() throws IOException {
+        File[] files = cacheDir.listFiles();
+        for (File f : files) {
+            String node = filenameEncoder.decode(f.getName());
+            DiscoverInfo info = restoreInfoFromFile(f);
+            if (info == null)
+                continue;
+
+            EntityCapsManager.addDiscoverInfoByNode(node, info);
+        }
+    }
+
+    public void emptyCache() {
+        File[] files = cacheDir.listFiles();
+        for (File f : files) {
+            f.delete();
+        }
+    }
+
+    /**
+     * Writes the DiscoverInfo packet to an file
+     * 
+     * @param file
+     * @param info
+     * @throws IOException
+     */
+    private static void writeInfoToFile(File file, DiscoverInfo info) throws IOException {
+        DataOutputStream dos = new DataOutputStream(new FileOutputStream(file));
+        try {
+            dos.writeUTF(info.toXML());
+        } finally {
+            dos.close();
+        }
+    }
+
+    /**
+     * Tries to restore an DiscoverInfo packet from a file.
+     * 
+     * @param file
+     * @return
+     * @throws IOException
+     */
+    private static DiscoverInfo restoreInfoFromFile(File file) throws IOException {
+        DataInputStream dis = new DataInputStream(new FileInputStream(file));
+        String fileContent = null;
+        String id;
+        String from;
+        String to;
+
+        try {
+            fileContent = dis.readUTF();
+        } finally {
+            dis.close();
+        }
+        if (fileContent == null)
+            return null;
+
+        Reader reader = new StringReader(fileContent);
+        XmlPullParser parser;
+        try {
+            parser = XmlPullParserFactory.newInstance().newPullParser();
+            parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+            parser.setInput(reader);
+        } catch (XmlPullParserException xppe) {
+            xppe.printStackTrace();
+            return null;
+        }
+
+        DiscoverInfo iqPacket;
+        IQProvider provider = new DiscoverInfoProvider();
+
+        // Parse the IQ, we only need the id
+        try {
+            parser.next();
+            id = parser.getAttributeValue("", "id");
+            from = parser.getAttributeValue("", "from");
+            to = parser.getAttributeValue("", "to");
+            parser.next();
+        } catch (XmlPullParserException e1) {
+            return null;
+        }
+
+        try {
+            iqPacket = (DiscoverInfo) provider.parseIQ(parser);
+        } catch (Exception e) {
+            return null;
+        }
+
+        iqPacket.setPacketID(id);
+        iqPacket.setFrom(from);
+        iqPacket.setTo(to);
+        iqPacket.setType(IQ.Type.RESULT);
+        return iqPacket;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/entitycaps/packet/CapsExtension.java b/src/org/jivesoftware/smackx/entitycaps/packet/CapsExtension.java
new file mode 100644
index 0000000..a87c86c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/entitycaps/packet/CapsExtension.java
@@ -0,0 +1,83 @@
+/**
+ * Copyright 2009 Jonas Ådahl.
+ * Copyright 2011-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.entitycaps.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.entitycaps.EntityCapsManager;
+
+public class CapsExtension implements PacketExtension {
+
+    private String node, ver, hash;
+
+    public CapsExtension() {
+    }
+
+    public CapsExtension(String node, String version, String hash) {
+        this.node = node;
+        this.ver = version;
+        this.hash = hash;
+    }
+
+    public String getElementName() {
+        return EntityCapsManager.ELEMENT;
+    }
+
+    public String getNamespace() {
+        return EntityCapsManager.NAMESPACE;
+    }
+
+    public String getNode() {
+        return node;
+    }
+
+    public void setNode(String node) {
+        this.node = node;
+    }
+
+    public String getVer() {
+        return ver;
+    }
+
+    public void setVer(String ver) {
+        this.ver = ver;
+    }
+
+    public String getHash() {
+        return hash;
+    }
+
+    public void setHash(String hash) {
+        this.hash = hash;
+    }
+
+    /*
+     *  <c xmlns='http://jabber.org/protocol/caps'
+     *  hash='sha-1'
+     *  node='http://code.google.com/p/exodus'
+     *  ver='QgayPKawpkPSDYmwT/WM94uAlu0='/>
+     *
+     */
+    public String toXML() {
+        String xml = "<" + EntityCapsManager.ELEMENT + " xmlns=\"" + EntityCapsManager.NAMESPACE + "\" " +
+            "hash=\"" + hash + "\" " +
+            "node=\"" + node + "\" " +
+            "ver=\"" + ver + "\"/>";
+
+        return xml;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/entitycaps/provider/CapsExtensionProvider.java b/src/org/jivesoftware/smackx/entitycaps/provider/CapsExtensionProvider.java
new file mode 100644
index 0000000..a112cd5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/entitycaps/provider/CapsExtensionProvider.java
@@ -0,0 +1,60 @@
+/**
+ * Copyright 2009 Jonas Ådahl.
+ * Copyright 2011-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.entitycaps.provider;
+
+import java.io.IOException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.entitycaps.EntityCapsManager;
+import org.jivesoftware.smackx.entitycaps.packet.CapsExtension;
+
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+public class CapsExtensionProvider implements PacketExtensionProvider {
+
+    public PacketExtension parseExtension(XmlPullParser parser) throws XmlPullParserException, IOException,
+            XMPPException {
+        String hash = null;
+        String version = null;
+        String node = null;
+        if (parser.getEventType() == XmlPullParser.START_TAG
+                && parser.getName().equalsIgnoreCase(EntityCapsManager.ELEMENT)) {
+            hash = parser.getAttributeValue(null, "hash");
+            version = parser.getAttributeValue(null, "ver");
+            node = parser.getAttributeValue(null, "node");
+        } else {
+            throw new XMPPException("Malformed Caps element");
+        }
+
+        parser.next();
+
+        if (!(parser.getEventType() == XmlPullParser.END_TAG
+                && parser.getName().equalsIgnoreCase(EntityCapsManager.ELEMENT))) {
+            throw new XMPPException("Malformed nested Caps element");
+        }
+
+        if (hash != null && version != null && node != null) {
+            return new CapsExtension(node, version, hash);
+        } else {
+            throw new XMPPException("Caps elment with missing attributes");
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java b/src/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java
new file mode 100644
index 0000000..22b5b1d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FaultTolerantNegotiator.java
@@ -0,0 +1,186 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.OrFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.concurrent.*;
+import java.util.List;
+import java.util.ArrayList;
+
+
+/**
+ * The fault tolerant negotiator takes two stream negotiators, the primary and the secondary
+ * negotiator. If the primary negotiator fails during the stream negotiaton process, the second
+ * negotiator is used.
+ */
+public class FaultTolerantNegotiator extends StreamNegotiator {
+
+    private StreamNegotiator primaryNegotiator;
+    private StreamNegotiator secondaryNegotiator;
+    private Connection connection;
+    private PacketFilter primaryFilter;
+    private PacketFilter secondaryFilter;
+
+    public FaultTolerantNegotiator(Connection connection, StreamNegotiator primary,
+            StreamNegotiator secondary) {
+        this.primaryNegotiator = primary;
+        this.secondaryNegotiator = secondary;
+        this.connection = connection;
+    }
+
+    public PacketFilter getInitiationPacketFilter(String from, String streamID) {
+        if (primaryFilter == null || secondaryFilter == null) {
+            primaryFilter = primaryNegotiator.getInitiationPacketFilter(from, streamID);
+            secondaryFilter = secondaryNegotiator.getInitiationPacketFilter(from, streamID);
+        }
+        return new OrFilter(primaryFilter, secondaryFilter);
+    }
+
+    InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException {
+        throw new UnsupportedOperationException("Negotiation only handled by create incoming " +
+                "stream method.");
+    }
+
+    final Packet initiateIncomingStream(Connection connection, StreamInitiation initiation) {
+        throw new UnsupportedOperationException("Initiation handled by createIncomingStream " +
+                "method");
+    }
+
+    public InputStream createIncomingStream(StreamInitiation initiation) throws XMPPException {
+        PacketCollector collector = connection.createPacketCollector(
+                getInitiationPacketFilter(initiation.getFrom(), initiation.getSessionID()));
+
+        connection.sendPacket(super.createInitiationAccept(initiation, getNamespaces()));
+
+        ExecutorService threadPoolExecutor = Executors.newFixedThreadPool(2);
+        CompletionService<InputStream> service
+                = new ExecutorCompletionService<InputStream>(threadPoolExecutor);
+        List<Future<InputStream>> futures = new ArrayList<Future<InputStream>>();
+        InputStream stream = null;
+        XMPPException exception = null;
+        try {
+            futures.add(service.submit(new NegotiatorService(collector)));
+            futures.add(service.submit(new NegotiatorService(collector)));
+
+            int i = 0;
+            while (stream == null && i < futures.size()) {
+                Future<InputStream> future;
+                try {
+                    i++;
+                    future = service.poll(10, TimeUnit.SECONDS);
+                }
+                catch (InterruptedException e) {
+                    continue;
+                }
+
+                if (future == null) {
+                    continue;
+                }
+
+                try {
+                    stream = future.get();
+                }
+                catch (InterruptedException e) {
+                    /* Do Nothing */
+                }
+                catch (ExecutionException e) {
+                    exception = new XMPPException(e.getCause());
+                }
+            }
+        }
+        finally {
+            for (Future<InputStream> future : futures) {
+                future.cancel(true);
+            }
+            collector.cancel();
+            threadPoolExecutor.shutdownNow();
+        }
+        if (stream == null) {
+            if (exception != null) {
+                throw exception;
+            }
+            else {
+                throw new XMPPException("File transfer negotiation failed.");
+            }
+        }
+
+        return stream;
+    }
+
+    private StreamNegotiator determineNegotiator(Packet streamInitiation) {
+        return primaryFilter.accept(streamInitiation) ? primaryNegotiator : secondaryNegotiator;
+    }
+
+    public OutputStream createOutgoingStream(String streamID, String initiator, String target)
+            throws XMPPException {
+        OutputStream stream;
+        try {
+            stream = primaryNegotiator.createOutgoingStream(streamID, initiator, target);
+        }
+        catch (XMPPException ex) {
+            stream = secondaryNegotiator.createOutgoingStream(streamID, initiator, target);
+        }
+
+        return stream;
+    }
+
+    public String[] getNamespaces() {
+        String[] primary = primaryNegotiator.getNamespaces();
+        String[] secondary = secondaryNegotiator.getNamespaces();
+
+        String[] namespaces = new String[primary.length + secondary.length];
+        System.arraycopy(primary, 0, namespaces, 0, primary.length);
+        System.arraycopy(secondary, 0, namespaces, primary.length, secondary.length);
+
+        return namespaces;
+    }
+
+    public void cleanup() {
+    }
+
+    private class NegotiatorService implements Callable<InputStream> {
+
+        private PacketCollector collector;
+
+        NegotiatorService(PacketCollector collector) {
+            this.collector = collector;
+        }
+
+        public InputStream call() throws Exception {
+            Packet streamInitiation = collector.nextResult(
+                    SmackConfiguration.getPacketReplyTimeout() * 2);
+            if (streamInitiation == null) {
+                throw new XMPPException("No response from remote client");
+            }
+            StreamNegotiator negotiator = determineNegotiator(streamInitiation);
+            return negotiator.negotiateIncomingStream(streamInitiation);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FileTransfer.java b/src/org/jivesoftware/smackx/filetransfer/FileTransfer.java
new file mode 100644
index 0000000..b840fd5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FileTransfer.java
@@ -0,0 +1,380 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.XMPPException;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+
+/**
+ * Contains the generic file information and progress related to a particular
+ * file transfer.
+ *
+ * @author Alexander Wenckus
+ *
+ */
+public abstract class FileTransfer {
+
+	private String fileName;
+
+	private String filePath;
+
+	private long fileSize;
+
+	private String peer;
+
+	private Status status = Status.initial;
+
+    private final Object statusMonitor = new Object();
+
+	protected FileTransferNegotiator negotiator;
+
+	protected String streamID;
+
+	protected long amountWritten = -1;
+
+	private Error error;
+
+	private Exception exception;
+
+    /**
+     * Buffer size between input and output
+     */
+    private static final int BUFFER_SIZE = 8192;
+
+    protected FileTransfer(String peer, String streamID,
+			FileTransferNegotiator negotiator) {
+		this.peer = peer;
+		this.streamID = streamID;
+		this.negotiator = negotiator;
+	}
+
+	protected void setFileInfo(String fileName, long fileSize) {
+		this.fileName = fileName;
+		this.fileSize = fileSize;
+	}
+
+	protected void setFileInfo(String path, String fileName, long fileSize) {
+		this.filePath = path;
+		this.fileName = fileName;
+		this.fileSize = fileSize;
+	}
+
+	/**
+	 * Returns the size of the file being transfered.
+	 *
+	 * @return Returns the size of the file being transfered.
+	 */
+	public long getFileSize() {
+		return fileSize;
+	}
+
+	/**
+	 * Returns the name of the file being transfered.
+	 *
+	 * @return Returns the name of the file being transfered.
+	 */
+	public String getFileName() {
+		return fileName;
+	}
+
+	/**
+	 * Returns the local path of the file.
+	 *
+	 * @return Returns the local path of the file.
+	 */
+	public String getFilePath() {
+		return filePath;
+	}
+
+	/**
+	 * Returns the JID of the peer for this file transfer.
+	 *
+	 * @return Returns the JID of the peer for this file transfer.
+	 */
+	public String getPeer() {
+		return peer;
+	}
+
+	/**
+	 * Returns the progress of the file transfer as a number between 0 and 1.
+	 *
+	 * @return Returns the progress of the file transfer as a number between 0
+	 *         and 1.
+	 */
+	public double getProgress() {
+        if (amountWritten <= 0 || fileSize <= 0) {
+            return 0;
+        }
+        return (double) amountWritten / (double) fileSize;
+	}
+
+	/**
+	 * Returns true if the transfer has been cancelled, if it has stopped because
+	 * of a an error, or the transfer completed successfully.
+	 *
+	 * @return Returns true if the transfer has been cancelled, if it has stopped
+	 *         because of a an error, or the transfer completed successfully.
+	 */
+	public boolean isDone() {
+		return status == Status.cancelled || status == Status.error
+				|| status == Status.complete || status == Status.refused;
+	}
+
+	/**
+	 * Returns the current status of the file transfer.
+	 *
+	 * @return Returns the current status of the file transfer.
+	 */
+	public Status getStatus() {
+		return status;
+	}
+
+	protected void setError(Error type) {
+		this.error = type;
+	}
+
+	/**
+	 * When {@link #getStatus()} returns that there was an {@link Status#error}
+	 * during the transfer, the type of error can be retrieved through this
+	 * method.
+	 *
+	 * @return Returns the type of error that occurred if one has occurred.
+	 */
+	public Error getError() {
+		return error;
+	}
+
+	/**
+	 * If an exception occurs asynchronously it will be stored for later
+	 * retrieval. If there is an error there maybe an exception set.
+	 *
+	 * @return The exception that occurred or null if there was no exception.
+	 * @see #getError()
+	 */
+	public Exception getException() {
+		return exception;
+	}
+
+    public String getStreamID() {
+        return streamID;
+    }
+
+	/**
+	 * Cancels the file transfer.
+	 */
+	public abstract void cancel();
+
+	protected void setException(Exception exception) {
+		this.exception = exception;
+	}
+
+	protected void setStatus(Status status) {
+        synchronized (statusMonitor) {
+		    this.status = status;
+	    }
+    }
+
+    protected boolean updateStatus(Status oldStatus, Status newStatus) {
+        synchronized (statusMonitor) {
+            if (oldStatus != status) {
+                return false;
+            }
+            status = newStatus;
+            return true;
+        }
+    }
+
+	protected void writeToStream(final InputStream in, final OutputStream out)
+			throws XMPPException
+    {
+		final byte[] b = new byte[BUFFER_SIZE];
+		int count = 0;
+		amountWritten = 0;
+
+        do {
+			// write to the output stream
+			try {
+				out.write(b, 0, count);
+			} catch (IOException e) {
+				throw new XMPPException("error writing to output stream", e);
+			}
+
+			amountWritten += count;
+
+			// read more bytes from the input stream
+			try {
+				count = in.read(b);
+			} catch (IOException e) {
+				throw new XMPPException("error reading from input stream", e);
+			}
+		} while (count != -1 && !getStatus().equals(Status.cancelled));
+
+		// the connection was likely terminated abrubtly if these are not equal
+		if (!getStatus().equals(Status.cancelled) && getError() == Error.none
+				&& amountWritten != fileSize) {
+            setStatus(Status.error);
+			this.error = Error.connection;
+		}
+	}
+
+	/**
+	 * A class to represent the current status of the file transfer.
+	 *
+	 * @author Alexander Wenckus
+	 *
+	 */
+	public enum Status {
+
+		/**
+		 * An error occurred during the transfer.
+		 *
+		 * @see FileTransfer#getError()
+		 */
+		error("Error"),
+
+		/**
+         * The initial status of the file transfer.
+         */
+        initial("Initial"),
+
+        /**
+		 * The file transfer is being negotiated with the peer. The party
+		 * Receiving the file has the option to accept or refuse a file transfer
+		 * request. If they accept, then the process of stream negotiation will
+		 * begin. If they refuse the file will not be transfered.
+		 *
+		 * @see #negotiating_stream
+		 */
+		negotiating_transfer("Negotiating Transfer"),
+
+		/**
+		 * The peer has refused the file transfer request halting the file
+		 * transfer negotiation process.
+		 */
+		refused("Refused"),
+
+		/**
+		 * The stream to transfer the file is being negotiated over the chosen
+		 * stream type. After the stream negotiating process is complete the
+		 * status becomes negotiated.
+		 *
+		 * @see #negotiated
+		 */
+		negotiating_stream("Negotiating Stream"),
+
+		/**
+		 * After the stream negotiation has completed the intermediate state
+		 * between the time when the negotiation is finished and the actual
+		 * transfer begins.
+		 */
+		negotiated("Negotiated"),
+
+		/**
+		 * The transfer is in progress.
+		 *
+		 * @see FileTransfer#getProgress()
+		 */
+		in_progress("In Progress"),
+
+		/**
+		 * The transfer has completed successfully.
+		 */
+		complete("Complete"),
+
+		/**
+		 * The file transfer was cancelled
+		 */
+		cancelled("Cancelled");
+
+        private String status;
+
+        private Status(String status) {
+            this.status = status;
+        }
+
+        public String toString() {
+            return status;
+        }
+    }
+
+    /**
+     * Return the length of bytes written out to the stream.
+     * @return the amount in bytes written out.
+     */
+    public long getAmountWritten(){
+        return amountWritten;
+    }
+
+    public enum Error {
+		/**
+		 * No error
+		 */
+		none("No error"),
+
+		/**
+		 * The peer did not find any of the provided stream mechanisms
+		 * acceptable.
+		 */
+		not_acceptable("The peer did not find any of the provided stream mechanisms acceptable."),
+
+		/**
+		 * The provided file to transfer does not exist or could not be read.
+		 */
+		bad_file("The provided file to transfer does not exist or could not be read."),
+
+		/**
+		 * The remote user did not respond or the connection timed out.
+		 */
+		no_response("The remote user did not respond or the connection timed out."),
+
+		/**
+		 * An error occurred over the socket connected to send the file.
+		 */
+		connection("An error occured over the socket connected to send the file."),
+
+		/**
+		 * An error occurred while sending or receiving the file
+		 */
+		stream("An error occured while sending or recieving the file.");
+
+		private final String msg;
+
+		private Error(String msg) {
+			this.msg = msg;
+		}
+
+		/**
+		 * Returns a String representation of this error.
+		 *
+		 * @return Returns a String representation of this error.
+		 */
+		public String getMessage() {
+			return msg;
+		}
+
+		public String toString() {
+			return msg;
+		}
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FileTransferListener.java b/src/org/jivesoftware/smackx/filetransfer/FileTransferListener.java
new file mode 100644
index 0000000..8e07543
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FileTransferListener.java
@@ -0,0 +1,36 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+/**
+ * File transfers can cause several events to be raised. These events can be
+ * monitored through this interface.
+ * 
+ * @author Alexander Wenckus
+ */
+public interface FileTransferListener {
+	/**
+	 * A request to send a file has been recieved from another user.
+	 * 
+	 * @param request
+	 *            The request from the other user.
+	 */
+	public void fileTransferRequest(final FileTransferRequest request);
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FileTransferManager.java b/src/org/jivesoftware/smackx/filetransfer/FileTransferManager.java
new file mode 100644
index 0000000..6e413fa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FileTransferManager.java
@@ -0,0 +1,182 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.IQTypeFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * The file transfer manager class handles the sending and recieving of files.
+ * To send a file invoke the {@link #createOutgoingFileTransfer(String)} method.
+ * <p>
+ * And to recieve a file add a file transfer listener to the manager. The
+ * listener will notify you when there is a new file transfer request. To create
+ * the {@link IncomingFileTransfer} object accept the transfer, or, if the
+ * transfer is not desirable reject it.
+ * 
+ * @author Alexander Wenckus
+ * 
+ */
+public class FileTransferManager {
+
+	private final FileTransferNegotiator fileTransferNegotiator;
+
+	private List<FileTransferListener> listeners;
+
+	private Connection connection;
+
+	/**
+	 * Creates a file transfer manager to initiate and receive file transfers.
+	 * 
+	 * @param connection
+	 *            The Connection that the file transfers will use.
+	 */
+	public FileTransferManager(Connection connection) {
+		this.connection = connection;
+		this.fileTransferNegotiator = FileTransferNegotiator
+				.getInstanceFor(connection);
+	}
+
+	/**
+	 * Add a file transfer listener to listen to incoming file transfer
+	 * requests.
+	 * 
+	 * @param li
+	 *            The listener
+	 * @see #removeFileTransferListener(FileTransferListener)
+	 * @see FileTransferListener
+	 */
+	public void addFileTransferListener(final FileTransferListener li) {
+		if (listeners == null) {
+			initListeners();
+		}
+		synchronized (this.listeners) {
+			listeners.add(li);
+		}
+	}
+
+	private void initListeners() {
+		listeners = new ArrayList<FileTransferListener>();
+
+		connection.addPacketListener(new PacketListener() {
+			public void processPacket(Packet packet) {
+				fireNewRequest((StreamInitiation) packet);
+			}
+		}, new AndFilter(new PacketTypeFilter(StreamInitiation.class),
+				new IQTypeFilter(IQ.Type.SET)));
+	}
+
+	protected void fireNewRequest(StreamInitiation initiation) {
+		FileTransferListener[] listeners = null;
+		synchronized (this.listeners) {
+			listeners = new FileTransferListener[this.listeners.size()];
+			this.listeners.toArray(listeners);
+		}
+		FileTransferRequest request = new FileTransferRequest(this, initiation);
+		for (int i = 0; i < listeners.length; i++) {
+			listeners[i].fileTransferRequest(request);
+		}
+	}
+
+	/**
+	 * Removes a file transfer listener.
+	 * 
+	 * @param li
+	 *            The file transfer listener to be removed
+	 * @see FileTransferListener
+	 */
+	public void removeFileTransferListener(final FileTransferListener li) {
+		if (listeners == null) {
+			return;
+		}
+		synchronized (this.listeners) {
+			listeners.remove(li);
+		}
+	}
+
+	/**
+	 * Creates an OutgoingFileTransfer to send a file to another user.
+	 * 
+	 * @param userID
+	 *            The fully qualified jabber ID (i.e. full JID) with resource of the user to
+	 *            send the file to.
+	 * @return The send file object on which the negotiated transfer can be run.
+	 * @exception IllegalArgumentException if userID is null or not a full JID
+	 */
+	public OutgoingFileTransfer createOutgoingFileTransfer(String userID) {
+        if (userID == null) {
+            throw new IllegalArgumentException("userID was null");
+        }
+        // We need to create outgoing file transfers with a full JID since this method will later
+        // use XEP-0095 to negotiate the stream. This is done with IQ stanzas that need to be addressed to a full JID
+        // in order to reach an client entity.
+        else if (!StringUtils.isFullJID(userID)) {
+            throw new IllegalArgumentException("The provided user id was not a full JID (i.e. with resource part)");
+        }
+
+		return new OutgoingFileTransfer(connection.getUser(), userID,
+				fileTransferNegotiator.getNextStreamID(),
+				fileTransferNegotiator);
+	}
+
+	/**
+	 * When the file transfer request is acceptable, this method should be
+	 * invoked. It will create an IncomingFileTransfer which allows the
+	 * transmission of the file to procede.
+	 * 
+	 * @param request
+	 *            The remote request that is being accepted.
+	 * @return The IncomingFileTransfer which manages the download of the file
+	 *         from the transfer initiator.
+	 */
+	protected IncomingFileTransfer createIncomingFileTransfer(
+			FileTransferRequest request) {
+		if (request == null) {
+			throw new NullPointerException("RecieveRequest cannot be null");
+		}
+
+		IncomingFileTransfer transfer = new IncomingFileTransfer(request,
+                fileTransferNegotiator);
+		transfer.setFileInfo(request.getFileName(), request.getFileSize());
+
+		return transfer;
+	}
+
+	protected void rejectIncomingFileTransfer(FileTransferRequest request) {
+		StreamInitiation initiation = request.getStreamInitiation();
+
+		IQ rejection = FileTransferNegotiator.createIQ(
+				initiation.getPacketID(), initiation.getFrom(), initiation
+						.getTo(), IQ.Type.ERROR);
+		rejection.setError(new XMPPError(XMPPError.Condition.no_acceptable));
+		connection.sendPacket(rejection);
+	}
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java b/src/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java
new file mode 100644
index 0000000..d1fb7bf
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FileTransferNegotiator.java
@@ -0,0 +1,485 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import java.net.URLConnection;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Random;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+/**
+ * Manages the negotiation of file transfers according to JEP-0096. If a file is
+ * being sent the remote user chooses the type of stream under which the file
+ * will be sent.
+ *
+ * @author Alexander Wenckus
+ * @see <a href="http://xmpp.org/extensions/xep-0096.html">XEP-0096: SI File Transfer</a>
+ */
+public class FileTransferNegotiator {
+
+    // Static
+
+    private static final String[] NAMESPACE = {
+            "http://jabber.org/protocol/si/profile/file-transfer",
+            "http://jabber.org/protocol/si"};
+
+    private static final Map<Connection, FileTransferNegotiator> transferObject =
+            new ConcurrentHashMap<Connection, FileTransferNegotiator>();
+
+    private static final String STREAM_INIT_PREFIX = "jsi_";
+
+    protected static final String STREAM_DATA_FIELD_NAME = "stream-method";
+
+    private static final Random randomGenerator = new Random();
+
+    /**
+     * A static variable to use only offer IBB for file transfer. It is generally recommend to only
+     * set this variable to true for testing purposes as IBB is the backup file transfer method
+     * and shouldn't be used as the only transfer method in production systems.
+     */
+    public static boolean IBB_ONLY = (System.getProperty("ibb") != null);//true;
+
+    /**
+     * Returns the file transfer negotiator related to a particular connection.
+     * When this class is requested on a particular connection the file transfer
+     * service is automatically enabled.
+     *
+     * @param connection The connection for which the transfer manager is desired
+     * @return The IMFileTransferManager
+     */
+    public static FileTransferNegotiator getInstanceFor(
+            final Connection connection) {
+        if (connection == null) {
+            throw new IllegalArgumentException("Connection cannot be null");
+        }
+        if (!connection.isConnected()) {
+            return null;
+        }
+
+        if (transferObject.containsKey(connection)) {
+            return transferObject.get(connection);
+        }
+        else {
+            FileTransferNegotiator transfer = new FileTransferNegotiator(
+                    connection);
+            setServiceEnabled(connection, true);
+            transferObject.put(connection, transfer);
+            return transfer;
+        }
+    }
+
+    /**
+     * Enable the Jabber services related to file transfer on the particular
+     * connection.
+     *
+     * @param connection The connection on which to enable or disable the services.
+     * @param isEnabled  True to enable, false to disable.
+     */
+    public static void setServiceEnabled(final Connection connection,
+            final boolean isEnabled) {
+        ServiceDiscoveryManager manager = ServiceDiscoveryManager
+                .getInstanceFor(connection);
+
+        List<String> namespaces = new ArrayList<String>();
+        namespaces.addAll(Arrays.asList(NAMESPACE));
+        namespaces.add(InBandBytestreamManager.NAMESPACE);
+        if (!IBB_ONLY) {
+            namespaces.add(Socks5BytestreamManager.NAMESPACE);
+        }
+
+        for (String namespace : namespaces) {
+            if (isEnabled) {
+                if (!manager.includesFeature(namespace)) {
+                    manager.addFeature(namespace);
+                }
+            } else {
+                manager.removeFeature(namespace);
+            }
+        }
+        
+    }
+
+    /**
+     * Checks to see if all file transfer related services are enabled on the
+     * connection.
+     *
+     * @param connection The connection to check
+     * @return True if all related services are enabled, false if they are not.
+     */
+    public static boolean isServiceEnabled(final Connection connection) {
+        ServiceDiscoveryManager manager = ServiceDiscoveryManager
+                .getInstanceFor(connection);
+
+        List<String> namespaces = new ArrayList<String>();
+        namespaces.addAll(Arrays.asList(NAMESPACE));
+        namespaces.add(InBandBytestreamManager.NAMESPACE);
+        if (!IBB_ONLY) {
+            namespaces.add(Socks5BytestreamManager.NAMESPACE);
+        }
+
+        for (String namespace : namespaces) {
+            if (!manager.includesFeature(namespace)) {
+                return false;
+            }
+        }
+        return true;
+    }
+
+    /**
+     * A convenience method to create an IQ packet.
+     *
+     * @param ID   The packet ID of the
+     * @param to   To whom the packet is addressed.
+     * @param from From whom the packet is sent.
+     * @param type The IQ type of the packet.
+     * @return The created IQ packet.
+     */
+    public static IQ createIQ(final String ID, final String to,
+            final String from, final IQ.Type type) {
+        IQ iqPacket = new IQ() {
+            public String getChildElementXML() {
+                return null;
+            }
+        };
+        iqPacket.setPacketID(ID);
+        iqPacket.setTo(to);
+        iqPacket.setFrom(from);
+        iqPacket.setType(type);
+
+        return iqPacket;
+    }
+
+    /**
+     * Returns a collection of the supported transfer protocols.
+     *
+     * @return Returns a collection of the supported transfer protocols.
+     */
+    public static Collection<String> getSupportedProtocols() {
+        List<String> protocols = new ArrayList<String>();
+        protocols.add(InBandBytestreamManager.NAMESPACE);
+        if (!IBB_ONLY) {
+            protocols.add(Socks5BytestreamManager.NAMESPACE);
+        }
+        return Collections.unmodifiableList(protocols);
+    }
+
+    // non-static
+
+    private final Connection connection;
+
+    private final StreamNegotiator byteStreamTransferManager;
+
+    private final StreamNegotiator inbandTransferManager;
+
+    private FileTransferNegotiator(final Connection connection) {
+        configureConnection(connection);
+
+        this.connection = connection;
+        byteStreamTransferManager = new Socks5TransferNegotiator(connection);
+        inbandTransferManager = new IBBTransferNegotiator(connection);
+    }
+
+    private void configureConnection(final Connection connection) {
+        connection.addConnectionListener(new ConnectionListener() {
+            public void connectionClosed() {
+                cleanup(connection);
+            }
+
+            public void connectionClosedOnError(Exception e) {
+                cleanup(connection);
+            }
+
+            public void reconnectionFailed(Exception e) {
+                // ignore
+            }
+
+            public void reconnectionSuccessful() {
+                // ignore
+            }
+
+            public void reconnectingIn(int seconds) {
+                // ignore
+            }
+        });
+    }
+
+    private void cleanup(final Connection connection) {
+        if (transferObject.remove(connection) != null) {
+            inbandTransferManager.cleanup();
+        }
+    }
+
+    /**
+     * Selects an appropriate stream negotiator after examining the incoming file transfer request.
+     *
+     * @param request The related file transfer request.
+     * @return The file transfer object that handles the transfer
+     * @throws XMPPException If there are either no stream methods contained in the packet, or
+     *                       there is not an appropriate stream method.
+     */
+    public StreamNegotiator selectStreamNegotiator(
+            FileTransferRequest request) throws XMPPException {
+        StreamInitiation si = request.getStreamInitiation();
+        FormField streamMethodField = getStreamMethodField(si
+                .getFeatureNegotiationForm());
+
+        if (streamMethodField == null) {
+            String errorMessage = "No stream methods contained in packet.";
+            XMPPError error = new XMPPError(XMPPError.Condition.bad_request, errorMessage);
+            IQ iqPacket = createIQ(si.getPacketID(), si.getFrom(), si.getTo(),
+                    IQ.Type.ERROR);
+            iqPacket.setError(error);
+            connection.sendPacket(iqPacket);
+            throw new XMPPException(errorMessage, error);
+        }
+
+        // select the appropriate protocol
+
+        StreamNegotiator selectedStreamNegotiator;
+        try {
+            selectedStreamNegotiator = getNegotiator(streamMethodField);
+        }
+        catch (XMPPException e) {
+            IQ iqPacket = createIQ(si.getPacketID(), si.getFrom(), si.getTo(),
+                    IQ.Type.ERROR);
+            iqPacket.setError(e.getXMPPError());
+            connection.sendPacket(iqPacket);
+            throw e;
+        }
+
+        // return the appropriate negotiator
+
+        return selectedStreamNegotiator;
+    }
+
+    private FormField getStreamMethodField(DataForm form) {
+        FormField field = null;
+        for (Iterator<FormField> it = form.getFields(); it.hasNext();) {
+            field = it.next();
+            if (field.getVariable().equals(STREAM_DATA_FIELD_NAME)) {
+                break;
+            }
+            field = null;
+        }
+        return field;
+    }
+
+    private StreamNegotiator getNegotiator(final FormField field)
+            throws XMPPException {
+        String variable;
+        boolean isByteStream = false;
+        boolean isIBB = false;
+        for (Iterator<FormField.Option> it = field.getOptions(); it.hasNext();) {
+            variable = it.next().getValue();
+            if (variable.equals(Socks5BytestreamManager.NAMESPACE) && !IBB_ONLY) {
+                isByteStream = true;
+            }
+            else if (variable.equals(InBandBytestreamManager.NAMESPACE)) {
+                isIBB = true;
+            }
+        }
+
+        if (!isByteStream && !isIBB) {
+            XMPPError error = new XMPPError(XMPPError.Condition.bad_request,
+                    "No acceptable transfer mechanism");
+            throw new XMPPException(error.getMessage(), error);
+        }
+
+       //if (isByteStream && isIBB && field.getType().equals(FormField.TYPE_LIST_MULTI)) {
+        if (isByteStream && isIBB) { 
+            return new FaultTolerantNegotiator(connection,
+                    byteStreamTransferManager,
+                    inbandTransferManager);
+        }
+        else if (isByteStream) {
+            return byteStreamTransferManager;
+        }
+        else {
+            return inbandTransferManager;
+        }
+    }
+
+    /**
+     * Reject a stream initiation request from a remote user.
+     *
+     * @param si The Stream Initiation request to reject.
+     */
+    public void rejectStream(final StreamInitiation si) {
+        XMPPError error = new XMPPError(XMPPError.Condition.forbidden, "Offer Declined");
+        IQ iqPacket = createIQ(si.getPacketID(), si.getFrom(), si.getTo(),
+                IQ.Type.ERROR);
+        iqPacket.setError(error);
+        connection.sendPacket(iqPacket);
+    }
+
+    /**
+     * Returns a new, unique, stream ID to identify a file transfer.
+     *
+     * @return Returns a new, unique, stream ID to identify a file transfer.
+     */
+    public String getNextStreamID() {
+        StringBuilder buffer = new StringBuilder();
+        buffer.append(STREAM_INIT_PREFIX);
+        buffer.append(Math.abs(randomGenerator.nextLong()));
+
+        return buffer.toString();
+    }
+
+    /**
+     * Send a request to another user to send them a file. The other user has
+     * the option of, accepting, rejecting, or not responding to a received file
+     * transfer request.
+     * <p/>
+     * If they accept, the packet will contain the other user's chosen stream
+     * type to send the file across. The two choices this implementation
+     * provides to the other user for file transfer are <a
+     * href="http://www.jabber.org/jeps/jep-0065.html">SOCKS5 Bytestreams</a>,
+     * which is the preferred method of transfer, and <a
+     * href="http://www.jabber.org/jeps/jep-0047.html">In-Band Bytestreams</a>,
+     * which is the fallback mechanism.
+     * <p/>
+     * The other user may choose to decline the file request if they do not
+     * desire the file, their client does not support JEP-0096, or if there are
+     * no acceptable means to transfer the file.
+     * <p/>
+     * Finally, if the other user does not respond this method will return null
+     * after the specified timeout.
+     *
+     * @param userID          The userID of the user to whom the file will be sent.
+     * @param streamID        The unique identifier for this file transfer.
+     * @param fileName        The name of this file. Preferably it should include an
+     *                        extension as it is used to determine what type of file it is.
+     * @param size            The size, in bytes, of the file.
+     * @param desc            A description of the file.
+     * @param responseTimeout The amount of time, in milliseconds, to wait for the remote
+     *                        user to respond. If they do not respond in time, this
+     * @return Returns the stream negotiator selected by the peer.
+     * @throws XMPPException Thrown if there is an error negotiating the file transfer.
+     */
+    public StreamNegotiator negotiateOutgoingTransfer(final String userID,
+            final String streamID, final String fileName, final long size,
+            final String desc, int responseTimeout) throws XMPPException {
+        StreamInitiation si = new StreamInitiation();
+        si.setSesssionID(streamID);
+        si.setMimeType(URLConnection.guessContentTypeFromName(fileName));
+
+        StreamInitiation.File siFile = new StreamInitiation.File(fileName, size);
+        siFile.setDesc(desc);
+        si.setFile(siFile);
+
+        si.setFeatureNegotiationForm(createDefaultInitiationForm());
+
+        si.setFrom(connection.getUser());
+        si.setTo(userID);
+        si.setType(IQ.Type.SET);
+
+        PacketCollector collector = connection
+                .createPacketCollector(new PacketIDFilter(si.getPacketID()));
+        connection.sendPacket(si);
+        Packet siResponse = collector.nextResult(responseTimeout);
+        collector.cancel();
+
+        if (siResponse instanceof IQ) {
+            IQ iqResponse = (IQ) siResponse;
+            if (iqResponse.getType().equals(IQ.Type.RESULT)) {
+                StreamInitiation response = (StreamInitiation) siResponse;
+                return getOutgoingNegotiator(getStreamMethodField(response
+                        .getFeatureNegotiationForm()));
+
+            }
+            else if (iqResponse.getType().equals(IQ.Type.ERROR)) {
+                throw new XMPPException(iqResponse.getError());
+            }
+            else {
+                throw new XMPPException("File transfer response unreadable");
+            }
+        }
+        else {
+            return null;
+        }
+    }
+
+    private StreamNegotiator getOutgoingNegotiator(final FormField field)
+            throws XMPPException {
+        String variable;
+        boolean isByteStream = false;
+        boolean isIBB = false;
+        for (Iterator<String> it = field.getValues(); it.hasNext();) {
+            variable = it.next();
+            if (variable.equals(Socks5BytestreamManager.NAMESPACE) && !IBB_ONLY) {
+                isByteStream = true;
+            }
+            else if (variable.equals(InBandBytestreamManager.NAMESPACE)) {
+                isIBB = true;
+            }
+        }
+
+        if (!isByteStream && !isIBB) {
+            XMPPError error = new XMPPError(XMPPError.Condition.bad_request,
+                    "No acceptable transfer mechanism");
+            throw new XMPPException(error.getMessage(), error);
+        }
+
+        if (isByteStream && isIBB) {
+            return new FaultTolerantNegotiator(connection,
+                    byteStreamTransferManager, inbandTransferManager);
+        }
+        else if (isByteStream) {
+            return byteStreamTransferManager;
+        }
+        else {
+            return inbandTransferManager;
+        }
+    }
+
+    private DataForm createDefaultInitiationForm() {
+        DataForm form = new DataForm(Form.TYPE_FORM);
+        FormField field = new FormField(STREAM_DATA_FIELD_NAME);
+        field.setType(FormField.TYPE_LIST_SINGLE);
+        if (!IBB_ONLY) {
+            field.addOption(new FormField.Option(Socks5BytestreamManager.NAMESPACE));
+        }
+        field.addOption(new FormField.Option(InBandBytestreamManager.NAMESPACE));
+        form.addField(field);
+        return form;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/FileTransferRequest.java b/src/org/jivesoftware/smackx/filetransfer/FileTransferRequest.java
new file mode 100644
index 0000000..6b5ccd8
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/FileTransferRequest.java
@@ -0,0 +1,138 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+/**
+ * A request to send a file recieved from another user.
+ * 
+ * @author Alexander Wenckus
+ * 
+ */
+public class FileTransferRequest {
+	private final StreamInitiation streamInitiation;
+
+	private final FileTransferManager manager;
+
+	/**
+	 * A recieve request is constructed from the Stream Initiation request
+	 * received from the initator.
+	 * 
+	 * @param manager
+	 *            The manager handling this file transfer
+	 * 
+	 * @param si
+	 *            The Stream initiaton recieved from the initiator.
+	 */
+	public FileTransferRequest(FileTransferManager manager, StreamInitiation si) {
+		this.streamInitiation = si;
+		this.manager = manager;
+	}
+
+	/**
+	 * Returns the name of the file.
+	 * 
+	 * @return Returns the name of the file.
+	 */
+	public String getFileName() {
+		return streamInitiation.getFile().getName();
+	}
+
+	/**
+	 * Returns the size in bytes of the file.
+	 * 
+	 * @return Returns the size in bytes of the file.
+	 */
+	public long getFileSize() {
+		return streamInitiation.getFile().getSize();
+	}
+
+	/**
+	 * Returns the description of the file provided by the requestor.
+	 * 
+	 * @return Returns the description of the file provided by the requestor.
+	 */
+	public String getDescription() {
+		return streamInitiation.getFile().getDesc();
+	}
+
+	/**
+	 * Returns the mime-type of the file.
+	 * 
+	 * @return Returns the mime-type of the file.
+	 */
+	public String getMimeType() {
+		return streamInitiation.getMimeType();
+	}
+
+	/**
+	 * Returns the fully-qualified jabber ID of the user that requested this
+	 * file transfer.
+	 * 
+	 * @return Returns the fully-qualified jabber ID of the user that requested
+	 *         this file transfer.
+	 */
+	public String getRequestor() {
+		return streamInitiation.getFrom();
+	}
+
+	/**
+	 * Returns the stream ID that uniquely identifies this file transfer.
+	 * 
+	 * @return Returns the stream ID that uniquely identifies this file
+	 *         transfer.
+	 */
+	public String getStreamID() {
+		return streamInitiation.getSessionID();
+	}
+
+	/**
+	 * Returns the stream initiation packet that was sent by the requestor which
+	 * contains the parameters of the file transfer being transfer and also the
+	 * methods available to transfer the file.
+	 * 
+	 * @return Returns the stream initiation packet that was sent by the
+	 *         requestor which contains the parameters of the file transfer
+	 *         being transfer and also the methods available to transfer the
+	 *         file.
+	 */
+	protected StreamInitiation getStreamInitiation() {
+		return streamInitiation;
+	}
+
+	/**
+	 * Accepts this file transfer and creates the incoming file transfer.
+	 * 
+	 * @return Returns the <b><i>IncomingFileTransfer</b></i> on which the
+	 *         file transfer can be carried out.
+	 */
+	public IncomingFileTransfer accept() {
+		return manager.createIncomingFileTransfer(this);
+	}
+
+	/**
+	 * Rejects the file transfer request.
+	 */
+	public void reject() {
+		manager.rejectIncomingFileTransfer(this);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java b/src/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java
new file mode 100644
index 0000000..b32f49a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/IBBTransferNegotiator.java
@@ -0,0 +1,152 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.FromContainsFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamManager;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamRequest;
+import org.jivesoftware.smackx.bytestreams.ibb.InBandBytestreamSession;
+import org.jivesoftware.smackx.bytestreams.ibb.packet.Open;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+/**
+ * The In-Band Bytestream file transfer method, or IBB for short, transfers the
+ * file over the same XML Stream used by XMPP. It is the fall-back mechanism in
+ * case the SOCKS5 bytestream method of transferring files is not available.
+ * 
+ * @author Alexander Wenckus
+ * @author Henning Staib
+ * @see <a href="http://xmpp.org/extensions/xep-0047.html">XEP-0047: In-Band
+ *      Bytestreams (IBB)</a>
+ */
+public class IBBTransferNegotiator extends StreamNegotiator {
+
+    private Connection connection;
+
+    private InBandBytestreamManager manager;
+
+    /**
+     * The default constructor for the In-Band Bytestream Negotiator.
+     * 
+     * @param connection The connection which this negotiator works on.
+     */
+    protected IBBTransferNegotiator(Connection connection) {
+        this.connection = connection;
+        this.manager = InBandBytestreamManager.getByteStreamManager(connection);
+    }
+
+    public OutputStream createOutgoingStream(String streamID, String initiator,
+                    String target) throws XMPPException {
+        InBandBytestreamSession session = this.manager.establishSession(target, streamID);
+        session.setCloseBothStreamsEnabled(true);
+        return session.getOutputStream();
+    }
+
+    public InputStream createIncomingStream(StreamInitiation initiation)
+                    throws XMPPException {
+        /*
+         * In-Band Bytestream initiation listener must ignore next in-band
+         * bytestream request with given session ID
+         */
+        this.manager.ignoreBytestreamRequestOnce(initiation.getSessionID());
+
+        Packet streamInitiation = initiateIncomingStream(this.connection, initiation);
+        return negotiateIncomingStream(streamInitiation);
+    }
+
+    public PacketFilter getInitiationPacketFilter(String from, String streamID) {
+        /*
+         * this method is always called prior to #negotiateIncomingStream() so
+         * the In-Band Bytestream initiation listener must ignore the next
+         * In-Band Bytestream request with the given session ID
+         */
+        this.manager.ignoreBytestreamRequestOnce(streamID);
+
+        return new AndFilter(new FromContainsFilter(from), new IBBOpenSidFilter(streamID));
+    }
+
+    public String[] getNamespaces() {
+        return new String[] { InBandBytestreamManager.NAMESPACE };
+    }
+
+    InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException {
+        // build In-Band Bytestream request
+        InBandBytestreamRequest request = new ByteStreamRequest(this.manager,
+                        (Open) streamInitiation);
+
+        // always accept the request
+        InBandBytestreamSession session = request.accept();
+        session.setCloseBothStreamsEnabled(true);
+        return session.getInputStream();
+    }
+
+    public void cleanup() {
+    }
+
+    /**
+     * This PacketFilter accepts an incoming In-Band Bytestream open request
+     * with a specified session ID.
+     */
+    private static class IBBOpenSidFilter extends PacketTypeFilter {
+
+        private String sessionID;
+
+        public IBBOpenSidFilter(String sessionID) {
+            super(Open.class);
+            if (sessionID == null) {
+                throw new IllegalArgumentException("StreamID cannot be null");
+            }
+            this.sessionID = sessionID;
+        }
+
+        public boolean accept(Packet packet) {
+            if (super.accept(packet)) {
+                Open bytestream = (Open) packet;
+
+                // packet must by of type SET and contains the given session ID
+                return this.sessionID.equals(bytestream.getSessionID())
+                                && IQ.Type.SET.equals(bytestream.getType());
+            }
+            return false;
+        }
+    }
+
+    /**
+     * Derive from InBandBytestreamRequest to access protected constructor.
+     */
+    private static class ByteStreamRequest extends InBandBytestreamRequest {
+
+        private ByteStreamRequest(InBandBytestreamManager manager, Open byteStreamRequest) {
+            super(manager, byteStreamRequest);
+        }
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java b/src/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java
new file mode 100644
index 0000000..91a5a0d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/IncomingFileTransfer.java
@@ -0,0 +1,215 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.XMPPException;
+
+import java.io.*;
+import java.util.concurrent.*;
+
+/**
+ * An incoming file transfer is created when the
+ * {@link FileTransferManager#createIncomingFileTransfer(FileTransferRequest)}
+ * method is invoked. It is a file being sent to the local user from another
+ * user on the jabber network. There are two stages of the file transfer to be
+ * concerned with and they can be handled in different ways depending upon the
+ * method that is invoked on this class.
+ * <p/>
+ * The first way that a file is recieved is by calling the
+ * {@link #recieveFile()} method. This method, negotiates the appropriate stream
+ * method and then returns the <b><i>InputStream</b></i> to read the file
+ * data from.
+ * <p/>
+ * The second way that a file can be recieved through this class is by invoking
+ * the {@link #recieveFile(File)} method. This method returns immediatly and
+ * takes as its parameter a file on the local file system where the file
+ * recieved from the transfer will be put.
+ *
+ * @author Alexander Wenckus
+ */
+public class IncomingFileTransfer extends FileTransfer {
+
+    private FileTransferRequest recieveRequest;
+
+    private InputStream inputStream;
+
+    protected IncomingFileTransfer(FileTransferRequest request,
+            FileTransferNegotiator transferNegotiator) {
+        super(request.getRequestor(), request.getStreamID(), transferNegotiator);
+        this.recieveRequest = request;
+    }
+
+    /**
+     * Negotiates the stream method to transfer the file over and then returns
+     * the negotiated stream.
+     *
+     * @return The negotiated InputStream from which to read the data.
+     * @throws XMPPException If there is an error in the negotiation process an exception
+     *                       is thrown.
+     */
+    public InputStream recieveFile() throws XMPPException {
+        if (inputStream != null) {
+            throw new IllegalStateException("Transfer already negotiated!");
+        }
+
+        try {
+            inputStream = negotiateStream();
+        }
+        catch (XMPPException e) {
+            setException(e);
+            throw e;
+        }
+
+        return inputStream;
+    }
+
+    /**
+     * This method negotitates the stream and then transfer's the file over the
+     * negotiated stream. The transfered file will be saved at the provided
+     * location.
+     * <p/>
+     * This method will return immedialtly, file transfer progress can be
+     * monitored through several methods:
+     * <p/>
+     * <UL>
+     * <LI>{@link FileTransfer#getStatus()}
+     * <LI>{@link FileTransfer#getProgress()}
+     * <LI>{@link FileTransfer#isDone()}
+     * </UL>
+     *
+     * @param file The location to save the file.
+     * @throws XMPPException            when the file transfer fails
+     * @throws IllegalArgumentException This exception is thrown when the the provided file is
+     *                                  either null, or cannot be written to.
+     */
+    public void recieveFile(final File file) throws XMPPException {
+        if (file != null) {
+            if (!file.exists()) {
+                try {
+                    file.createNewFile();
+                }
+                catch (IOException e) {
+                    throw new XMPPException(
+                            "Could not create file to write too", e);
+                }
+            }
+            if (!file.canWrite()) {
+                throw new IllegalArgumentException("Cannot write to provided file");
+            }
+        }
+        else {
+            throw new IllegalArgumentException("File cannot be null");
+        }
+
+        Thread transferThread = new Thread(new Runnable() {
+            public void run() {
+                try {
+                    inputStream = negotiateStream();
+                }
+                catch (XMPPException e) {
+                    handleXMPPException(e);
+                    return;
+                }
+
+                OutputStream outputStream = null;
+                try {
+                    outputStream = new FileOutputStream(file);
+                    setStatus(Status.in_progress);
+                    writeToStream(inputStream, outputStream);
+                }
+                catch (XMPPException e) {
+                    setStatus(Status.error);
+                    setError(Error.stream);
+                    setException(e);
+                }
+                catch (FileNotFoundException e) {
+                    setStatus(Status.error);
+                    setError(Error.bad_file);
+                    setException(e);
+                }
+
+                if (getStatus().equals(Status.in_progress)) {
+                    setStatus(Status.complete);
+                }
+                if (inputStream != null) {
+                    try {
+                        inputStream.close();
+                    }
+                    catch (Throwable io) {
+                        /* Ignore */
+                    }
+                }
+                if (outputStream != null) {
+                    try {
+                        outputStream.close();
+                    }
+                    catch (Throwable io) {
+                        /* Ignore */
+                    }
+                }
+            }
+        }, "File Transfer " + streamID);
+        transferThread.start();
+    }
+
+    private void handleXMPPException(XMPPException e) {
+        setStatus(FileTransfer.Status.error);
+        setException(e);
+    }
+
+    private InputStream negotiateStream() throws XMPPException {
+        setStatus(Status.negotiating_transfer);
+        final StreamNegotiator streamNegotiator = negotiator
+                .selectStreamNegotiator(recieveRequest);
+        setStatus(Status.negotiating_stream);
+        FutureTask<InputStream> streamNegotiatorTask = new FutureTask<InputStream>(
+                new Callable<InputStream>() {
+
+                    public InputStream call() throws Exception {
+                        return streamNegotiator
+                                .createIncomingStream(recieveRequest.getStreamInitiation());
+                    }
+                });
+        streamNegotiatorTask.run();
+        InputStream inputStream;
+        try {
+            inputStream = streamNegotiatorTask.get(15, TimeUnit.SECONDS);
+        }
+        catch (InterruptedException e) {
+            throw new XMPPException("Interruption while executing", e);
+        }
+        catch (ExecutionException e) {
+            throw new XMPPException("Error in execution", e);
+        }
+        catch (TimeoutException e) {
+            throw new XMPPException("Request timed out", e);
+        }
+        finally {
+            streamNegotiatorTask.cancel(true);
+        }
+        setStatus(Status.negotiated);
+        return inputStream;
+    }
+
+    public void cancel() {
+        setStatus(Status.cancelled);
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java b/src/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java
new file mode 100644
index 0000000..bba6c38
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/OutgoingFileTransfer.java
@@ -0,0 +1,456 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.XMPPError;
+
+import java.io.*;
+
+/**
+ * Handles the sending of a file to another user. File transfer's in jabber have
+ * several steps and there are several methods in this class that handle these
+ * steps differently.
+ *
+ * @author Alexander Wenckus
+ *
+ */
+public class OutgoingFileTransfer extends FileTransfer {
+
+	private static int RESPONSE_TIMEOUT = 60 * 1000;
+    private NegotiationProgress callback;
+
+    /**
+     * Returns the time in milliseconds after which the file transfer
+     * negotiation process will timeout if the other user has not responded.
+     *
+     * @return Returns the time in milliseconds after which the file transfer
+     *         negotiation process will timeout if the remote user has not
+     *         responded.
+     */
+    public static int getResponseTimeout() {
+        return RESPONSE_TIMEOUT;
+    }
+
+	/**
+	 * Sets the time in milliseconds after which the file transfer negotiation
+	 * process will timeout if the other user has not responded.
+	 *
+	 * @param responseTimeout
+	 *            The timeout time in milliseconds.
+	 */
+	public static void setResponseTimeout(int responseTimeout) {
+		RESPONSE_TIMEOUT = responseTimeout;
+	}
+
+	private OutputStream outputStream;
+
+	private String initiator;
+
+	private Thread transferThread;
+
+	protected OutgoingFileTransfer(String initiator, String target,
+			String streamID, FileTransferNegotiator transferNegotiator) {
+		super(target, streamID, transferNegotiator);
+		this.initiator = initiator;
+	}
+
+	protected void setOutputStream(OutputStream stream) {
+		if (outputStream == null) {
+			this.outputStream = stream;
+		}
+	}
+
+	/**
+	 * Returns the output stream connected to the peer to transfer the file. It
+	 * is only available after it has been successfully negotiated by the
+	 * {@link StreamNegotiator}.
+	 *
+	 * @return Returns the output stream connected to the peer to transfer the
+	 *         file.
+	 */
+	protected OutputStream getOutputStream() {
+		if (getStatus().equals(FileTransfer.Status.negotiated)) {
+			return outputStream;
+		} else {
+			return null;
+		}
+	}
+
+	/**
+	 * This method handles the negotiation of the file transfer and the stream,
+	 * it only returns the created stream after the negotiation has been completed.
+	 *
+	 * @param fileName
+	 *            The name of the file that will be transmitted. It is
+	 *            preferable for this name to have an extension as it will be
+	 *            used to determine the type of file it is.
+	 * @param fileSize
+	 *            The size in bytes of the file that will be transmitted.
+	 * @param description
+	 *            A description of the file that will be transmitted.
+	 * @return The OutputStream that is connected to the peer to transmit the
+	 *         file.
+	 * @throws XMPPException
+	 *             Thrown if an error occurs during the file transfer
+	 *             negotiation process.
+	 */
+	public synchronized OutputStream sendFile(String fileName, long fileSize,
+			String description) throws XMPPException {
+		if (isDone() || outputStream != null) {
+			throw new IllegalStateException(
+					"The negotation process has already"
+							+ " been attempted on this file transfer");
+		}
+		try {
+			setFileInfo(fileName, fileSize);
+			this.outputStream = negotiateStream(fileName, fileSize, description);
+		} catch (XMPPException e) {
+			handleXMPPException(e);
+			throw e;
+		}
+		return outputStream;
+	}
+
+	/**
+	 * This methods handles the transfer and stream negotiation process. It
+	 * returns immediately and its progress will be updated through the
+	 * {@link NegotiationProgress} callback.
+	 *
+	 * @param fileName
+	 *            The name of the file that will be transmitted. It is
+	 *            preferable for this name to have an extension as it will be
+	 *            used to determine the type of file it is.
+	 * @param fileSize
+	 *            The size in bytes of the file that will be transmitted.
+	 * @param description
+	 *            A description of the file that will be transmitted.
+	 * @param progress
+	 *            A callback to monitor the progress of the file transfer
+	 *            negotiation process and to retrieve the OutputStream when it
+	 *            is complete.
+	 */
+	public synchronized void sendFile(final String fileName,
+			final long fileSize, final String description,
+			final NegotiationProgress progress)
+    {
+        if(progress == null) {
+            throw new IllegalArgumentException("Callback progress cannot be null.");
+        }
+        checkTransferThread();
+		if (isDone() || outputStream != null) {
+			throw new IllegalStateException(
+					"The negotation process has already"
+							+ " been attempted for this file transfer");
+		}
+        setFileInfo(fileName, fileSize);
+        this.callback = progress;
+        transferThread = new Thread(new Runnable() {
+			public void run() {
+				try {
+					OutgoingFileTransfer.this.outputStream = negotiateStream(
+							fileName, fileSize, description);
+                    progress.outputStreamEstablished(OutgoingFileTransfer.this.outputStream);
+                }
+                catch (XMPPException e) {
+					handleXMPPException(e);
+				}
+			}
+		}, "File Transfer Negotiation " + streamID);
+		transferThread.start();
+	}
+
+	private void checkTransferThread() {
+		if (transferThread != null && transferThread.isAlive() || isDone()) {
+			throw new IllegalStateException(
+					"File transfer in progress or has already completed.");
+		}
+	}
+
+    /**
+	 * This method handles the stream negotiation process and transmits the file
+	 * to the remote user. It returns immediately and the progress of the file
+	 * transfer can be monitored through several methods:
+	 *
+	 * <UL>
+	 * <LI>{@link FileTransfer#getStatus()}
+	 * <LI>{@link FileTransfer#getProgress()}
+	 * <LI>{@link FileTransfer#isDone()}
+	 * </UL>
+	 *
+     * @param file the file to transfer to the remote entity.
+     * @param description a description for the file to transfer.
+	 * @throws XMPPException
+	 *             If there is an error during the negotiation process or the
+	 *             sending of the file.
+	 */
+	public synchronized void sendFile(final File file, final String description)
+			throws XMPPException {
+		checkTransferThread();
+		if (file == null || !file.exists() || !file.canRead()) {
+			throw new IllegalArgumentException("Could not read file");
+		} else {
+			setFileInfo(file.getAbsolutePath(), file.getName(), file.length());
+		}
+
+		transferThread = new Thread(new Runnable() {
+			public void run() {
+				try {
+					outputStream = negotiateStream(file.getName(), file
+							.length(), description);
+				} catch (XMPPException e) {
+					handleXMPPException(e);
+					return;
+				}
+				if (outputStream == null) {
+					return;
+				}
+
+                if (!updateStatus(Status.negotiated, Status.in_progress)) {
+					return;
+				}
+
+				InputStream inputStream = null;
+				try {
+					inputStream = new FileInputStream(file);
+					writeToStream(inputStream, outputStream);
+				} catch (FileNotFoundException e) {
+					setStatus(FileTransfer.Status.error);
+					setError(Error.bad_file);
+					setException(e);
+				} catch (XMPPException e) {
+					setStatus(FileTransfer.Status.error);
+					setException(e);
+				} finally {
+					try {
+						if (inputStream != null) {
+							inputStream.close();
+						}
+
+						outputStream.flush();
+						outputStream.close();
+					} catch (IOException e) {
+                        /* Do Nothing */
+					}
+				}
+                updateStatus(Status.in_progress, FileTransfer.Status.complete);
+				}
+
+		}, "File Transfer " + streamID);
+		transferThread.start();
+	}
+
+    /**
+	 * This method handles the stream negotiation process and transmits the file
+	 * to the remote user. It returns immediately and the progress of the file
+	 * transfer can be monitored through several methods:
+	 *
+	 * <UL>
+	 * <LI>{@link FileTransfer#getStatus()}
+	 * <LI>{@link FileTransfer#getProgress()}
+	 * <LI>{@link FileTransfer#isDone()}
+	 * </UL>
+	 *
+     * @param in the stream to transfer to the remote entity.
+     * @param fileName the name of the file that is transferred
+     * @param fileSize the size of the file that is transferred
+     * @param description a description for the file to transfer.
+	 */
+	public synchronized void sendStream(final InputStream in, final String fileName, final long fileSize, final String description){
+		checkTransferThread();
+
+		setFileInfo(fileName, fileSize);
+		transferThread = new Thread(new Runnable() {
+			public void run() {
+                setFileInfo(fileName, fileSize);
+                //Create packet filter
+                try {
+					outputStream = negotiateStream(fileName, fileSize, description);
+				} catch (XMPPException e) {
+					handleXMPPException(e);
+					return;
+				} catch (IllegalStateException e) {
+					setStatus(FileTransfer.Status.error);
+					setException(e);
+				}
+				if (outputStream == null) {
+					return;
+				}
+
+                if (!updateStatus(Status.negotiated, Status.in_progress)) {
+					return;
+				}
+				try {
+					writeToStream(in, outputStream);
+				} catch (XMPPException e) {
+					setStatus(FileTransfer.Status.error);
+					setException(e);
+				} catch (IllegalStateException e) {
+					setStatus(FileTransfer.Status.error);
+					setException(e);
+				} finally {
+					try {
+						if (in != null) {
+							in.close();
+						}
+
+						outputStream.flush();
+						outputStream.close();
+					} catch (IOException e) {
+                        /* Do Nothing */
+					}
+				}
+                updateStatus(Status.in_progress, FileTransfer.Status.complete);
+				}
+
+		}, "File Transfer " + streamID);
+		transferThread.start();
+	}
+
+	private void handleXMPPException(XMPPException e) {
+		XMPPError error = e.getXMPPError();
+		if (error != null) {
+			int code = error.getCode();
+			if (code == 403) {
+				setStatus(Status.refused);
+				return;
+			}
+            else if (code == 400) {
+				setStatus(Status.error);
+				setError(Error.not_acceptable);
+            }
+            else {
+                setStatus(FileTransfer.Status.error);
+            }
+        }
+
+        setException(e);
+	}
+
+	/**
+	 * Returns the amount of bytes that have been sent for the file transfer. Or
+	 * -1 if the file transfer has not started.
+	 * <p>
+	 * Note: This method is only useful when the {@link #sendFile(File, String)}
+	 * method is called, as it is the only method that actually transmits the
+	 * file.
+	 *
+	 * @return Returns the amount of bytes that have been sent for the file
+	 *         transfer. Or -1 if the file transfer has not started.
+	 */
+	public long getBytesSent() {
+		return amountWritten;
+	}
+
+	private OutputStream negotiateStream(String fileName, long fileSize,
+			String description) throws XMPPException {
+		// Negotiate the file transfer profile
+
+        if (!updateStatus(Status.initial, Status.negotiating_transfer)) {
+            throw new XMPPException("Illegal state change");
+        }
+		StreamNegotiator streamNegotiator = negotiator.negotiateOutgoingTransfer(
+				getPeer(), streamID, fileName, fileSize, description,
+				RESPONSE_TIMEOUT);
+
+		if (streamNegotiator == null) {
+			setStatus(Status.error);
+			setError(Error.no_response);
+			return null;
+		}
+
+        // Negotiate the stream
+        if (!updateStatus(Status.negotiating_transfer, Status.negotiating_stream)) {
+            throw new XMPPException("Illegal state change");
+        }
+		outputStream = streamNegotiator.createOutgoingStream(streamID,
+                initiator, getPeer());
+
+        if (!updateStatus(Status.negotiating_stream, Status.negotiated)) {
+            throw new XMPPException("Illegal state change");
+		}
+		return outputStream;
+	}
+
+	public void cancel() {
+		setStatus(Status.cancelled);
+	}
+
+    @Override
+    protected boolean updateStatus(Status oldStatus, Status newStatus) {
+        boolean isUpdated = super.updateStatus(oldStatus, newStatus);
+        if(callback != null && isUpdated) {
+            callback.statusUpdated(oldStatus, newStatus);
+        }
+        return isUpdated;
+    }
+
+    @Override
+    protected void setStatus(Status status) {
+        Status oldStatus = getStatus();
+        super.setStatus(status);
+        if(callback != null) {
+            callback.statusUpdated(oldStatus, status);
+        }
+    }
+
+    @Override
+    protected void setException(Exception exception) {
+        super.setException(exception);
+        if(callback != null) {
+            callback.errorEstablishingStream(exception);
+        }
+    }
+
+    /**
+	 * A callback class to retrieve the status of an outgoing transfer
+	 * negotiation process.
+	 *
+	 * @author Alexander Wenckus
+	 *
+	 */
+	public interface NegotiationProgress {
+
+		/**
+		 * Called when the status changes
+         *
+         * @param oldStatus the previous status of the file transfer.
+         * @param newStatus the new status of the file transfer.
+         */
+		void statusUpdated(Status oldStatus, Status newStatus);
+
+		/**
+		 * Once the negotiation process is completed the output stream can be
+		 * retrieved.
+         *
+         * @param stream the established stream which can be used to transfer the file to the remote
+         * entity
+		 */
+		void outputStreamEstablished(OutputStream stream);
+
+        /**
+         * Called when an exception occurs during the negotiation progress.
+         *
+         * @param e the exception that occurred.
+         */
+        void errorEstablishingStream(Exception e);
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java b/src/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java
new file mode 100644
index 0000000..3c07fdc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/Socks5TransferNegotiator.java
@@ -0,0 +1,164 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.io.PushbackInputStream;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.FromMatchesFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamManager;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamRequest;
+import org.jivesoftware.smackx.bytestreams.socks5.Socks5BytestreamSession;
+import org.jivesoftware.smackx.bytestreams.socks5.packet.Bytestream;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+/**
+ * Negotiates a SOCKS5 Bytestream to be used for file transfers. The implementation is based on the
+ * {@link Socks5BytestreamManager} and the {@link Socks5BytestreamRequest}.
+ * 
+ * @author Henning Staib
+ * @see <a href="http://xmpp.org/extensions/xep-0065.html">XEP-0065: SOCKS5 Bytestreams</a>
+ */
+public class Socks5TransferNegotiator extends StreamNegotiator {
+
+    private Connection connection;
+
+    private Socks5BytestreamManager manager;
+
+    Socks5TransferNegotiator(Connection connection) {
+        this.connection = connection;
+        this.manager = Socks5BytestreamManager.getBytestreamManager(this.connection);
+    }
+
+    @Override
+    public OutputStream createOutgoingStream(String streamID, String initiator, String target)
+                    throws XMPPException {
+        try {
+            return this.manager.establishSession(target, streamID).getOutputStream();
+        }
+        catch (IOException e) {
+            throw new XMPPException("error establishing SOCKS5 Bytestream", e);
+        }
+        catch (InterruptedException e) {
+            throw new XMPPException("error establishing SOCKS5 Bytestream", e);
+        }
+    }
+
+    @Override
+    public InputStream createIncomingStream(StreamInitiation initiation) throws XMPPException,
+                    InterruptedException {
+        /*
+         * SOCKS5 initiation listener must ignore next SOCKS5 Bytestream request with given session
+         * ID
+         */
+        this.manager.ignoreBytestreamRequestOnce(initiation.getSessionID());
+
+        Packet streamInitiation = initiateIncomingStream(this.connection, initiation);
+        return negotiateIncomingStream(streamInitiation);
+    }
+
+    @Override
+    public PacketFilter getInitiationPacketFilter(final String from, String streamID) {
+        /*
+         * this method is always called prior to #negotiateIncomingStream() so the SOCKS5
+         * InitiationListener must ignore the next SOCKS5 Bytestream request with the given session
+         * ID
+         */
+        this.manager.ignoreBytestreamRequestOnce(streamID);
+
+        return new AndFilter(new FromMatchesFilter(from), new BytestreamSIDFilter(streamID));
+    }
+
+    @Override
+    public String[] getNamespaces() {
+        return new String[] { Socks5BytestreamManager.NAMESPACE };
+    }
+
+    @Override
+    InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException,
+                    InterruptedException {
+        // build SOCKS5 Bytestream request
+        Socks5BytestreamRequest request = new ByteStreamRequest(this.manager,
+                        (Bytestream) streamInitiation);
+
+        // always accept the request
+        Socks5BytestreamSession session = request.accept();
+
+        // test input stream
+        try {
+            PushbackInputStream stream = new PushbackInputStream(session.getInputStream());
+            int firstByte = stream.read();
+            stream.unread(firstByte);
+            return stream;
+        }
+        catch (IOException e) {
+            throw new XMPPException("Error establishing input stream", e);
+        }
+    }
+
+    @Override
+    public void cleanup() {
+        /* do nothing */
+    }
+
+    /**
+     * This PacketFilter accepts an incoming SOCKS5 Bytestream request with a specified session ID.
+     */
+    private static class BytestreamSIDFilter extends PacketTypeFilter {
+
+        private String sessionID;
+
+        public BytestreamSIDFilter(String sessionID) {
+            super(Bytestream.class);
+            if (sessionID == null) {
+                throw new IllegalArgumentException("StreamID cannot be null");
+            }
+            this.sessionID = sessionID;
+        }
+
+        @Override
+        public boolean accept(Packet packet) {
+            if (super.accept(packet)) {
+                Bytestream bytestream = (Bytestream) packet;
+
+                // packet must by of type SET and contains the given session ID
+                return this.sessionID.equals(bytestream.getSessionID())
+                                && IQ.Type.SET.equals(bytestream.getType());
+            }
+            return false;
+        }
+
+    }
+
+    /**
+     * Derive from Socks5BytestreamRequest to access protected constructor.
+     */
+    private static class ByteStreamRequest extends Socks5BytestreamRequest {
+
+        private ByteStreamRequest(Socks5BytestreamManager manager, Bytestream byteStreamRequest) {
+            super(manager, byteStreamRequest);
+        }
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java b/src/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java
new file mode 100644
index 0000000..5eefe43
--- /dev/null
+++ b/src/org/jivesoftware/smackx/filetransfer/StreamNegotiator.java
@@ -0,0 +1,167 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.filetransfer;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+
+/**
+ * After the file transfer negotiation process is completed according to
+ * JEP-0096, the negotiation process is passed off to a particular stream
+ * negotiator. The stream negotiator will then negotiate the chosen stream and
+ * return the stream to transfer the file.
+ *
+ * @author Alexander Wenckus
+ */
+public abstract class StreamNegotiator {
+
+    /**
+     * Creates the initiation acceptance packet to forward to the stream
+     * initiator.
+     *
+     * @param streamInitiationOffer The offer from the stream initiator to connect for a stream.
+     * @param namespaces            The namespace that relates to the accepted means of transfer.
+     * @return The response to be forwarded to the initiator.
+     */
+    public StreamInitiation createInitiationAccept(
+            StreamInitiation streamInitiationOffer, String[] namespaces)
+    {
+        StreamInitiation response = new StreamInitiation();
+        response.setTo(streamInitiationOffer.getFrom());
+        response.setFrom(streamInitiationOffer.getTo());
+        response.setType(IQ.Type.RESULT);
+        response.setPacketID(streamInitiationOffer.getPacketID());
+
+        DataForm form = new DataForm(Form.TYPE_SUBMIT);
+        FormField field = new FormField(
+                FileTransferNegotiator.STREAM_DATA_FIELD_NAME);
+        for (String namespace : namespaces) {
+            field.addValue(namespace);
+        }
+        form.addField(field);
+
+        response.setFeatureNegotiationForm(form);
+        return response;
+    }
+
+
+    public IQ createError(String from, String to, String packetID, XMPPError xmppError) {
+        IQ iq = FileTransferNegotiator.createIQ(packetID, to, from, IQ.Type.ERROR);
+        iq.setError(xmppError);
+        return iq;
+    }
+
+    Packet initiateIncomingStream(Connection connection, StreamInitiation initiation) throws XMPPException {
+        StreamInitiation response = createInitiationAccept(initiation,
+                getNamespaces());
+
+        // establish collector to await response
+        PacketCollector collector = connection
+                .createPacketCollector(getInitiationPacketFilter(initiation.getFrom(), initiation.getSessionID()));
+        connection.sendPacket(response);
+
+        Packet streamMethodInitiation = collector
+                .nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (streamMethodInitiation == null) {
+            throw new XMPPException("No response from file transfer initiator");
+        }
+
+        return streamMethodInitiation;
+    }
+
+    /**
+     * Returns the packet filter that will return the initiation packet for the appropriate stream
+     * initiation.
+     *
+     * @param from     The initiator of the file transfer.
+     * @param streamID The stream ID related to the transfer.
+     * @return The <b><i>PacketFilter</b></i> that will return the packet relatable to the stream
+     *         initiation.
+     */
+    public abstract PacketFilter getInitiationPacketFilter(String from, String streamID);
+
+
+    abstract InputStream negotiateIncomingStream(Packet streamInitiation) throws XMPPException,
+            InterruptedException;
+
+    /**
+     * This method handles the file stream download negotiation process. The
+     * appropriate stream negotiator's initiate incoming stream is called after
+     * an appropriate file transfer method is selected. The manager will respond
+     * to the initiator with the selected means of transfer, then it will handle
+     * any negotiation specific to the particular transfer method. This method
+     * returns the InputStream, ready to transfer the file.
+     *
+     * @param initiation The initiation that triggered this download.
+     * @return After the negotiation process is complete, the InputStream to
+     *         write a file to is returned.
+     * @throws XMPPException If an error occurs during this process an XMPPException is
+     *                       thrown.
+     * @throws InterruptedException If thread is interrupted.
+     */
+    public abstract InputStream createIncomingStream(StreamInitiation initiation)
+            throws XMPPException, InterruptedException;
+
+    /**
+     * This method handles the file upload stream negotiation process. The
+     * particular stream negotiator is determined during the file transfer
+     * negotiation process. This method returns the OutputStream to transmit the
+     * file to the remote user.
+     *
+     * @param streamID  The streamID that uniquely identifies the file transfer.
+     * @param initiator The fully-qualified JID of the initiator of the file transfer.
+     * @param target    The fully-qualified JID of the target or receiver of the file
+     *                  transfer.
+     * @return The negotiated stream ready for data.
+     * @throws XMPPException If an error occurs during the negotiation process an
+     *                       exception will be thrown.
+     */
+    public abstract OutputStream createOutgoingStream(String streamID,
+            String initiator, String target) throws XMPPException;
+
+    /**
+     * Returns the XMPP namespace reserved for this particular type of file
+     * transfer.
+     *
+     * @return Returns the XMPP namespace reserved for this particular type of
+     *         file transfer.
+     */
+    public abstract String[] getNamespaces();
+
+    /**
+     * Cleanup any and all resources associated with this negotiator.
+     */
+    public abstract void cleanup();
+
+}
diff --git a/src/org/jivesoftware/smackx/forward/Forwarded.java b/src/org/jivesoftware/smackx/forward/Forwarded.java
new file mode 100644
index 0000000..817ee27
--- /dev/null
+++ b/src/org/jivesoftware/smackx/forward/Forwarded.java
@@ -0,0 +1,125 @@
+/**
+ * Copyright 2013 Georg Lukas
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.forward;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.packet.DelayInfo;
+import org.jivesoftware.smackx.provider.DelayInfoProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Packet extension for XEP-0297: Stanza Forwarding. This class implements
+ * the packet extension and a {@link PacketExtensionProvider} to parse
+ * forwarded messages from a packet. The extension
+ * <a href="http://xmpp.org/extensions/xep-0297.html">XEP-0297</a> is
+ * a prerequisite for XEP-0280 (Message Carbons).
+ *
+ * <p>The {@link Forwarded.Provider} must be registered in the
+ * <b>smack.properties</b> file for the element <b>forwarded</b> with
+ * namespace <b>urn:xmpp:forwarded:0</b></p> to be used.
+ *
+ * @author Georg Lukas
+ */
+public class Forwarded implements PacketExtension {
+    public static final String NAMESPACE = "urn:xmpp:forward:0";
+    public static final String ELEMENT_NAME = "forwarded";
+
+    private DelayInfo delay;
+    private Packet forwardedPacket;
+
+    /**
+     * Creates a new Forwarded packet extension.
+     *
+     * @param delay an optional {@link DelayInfo} timestamp of the packet.
+     * @param fwdPacket the packet that is forwarded (required).
+     */
+    public Forwarded(DelayInfo delay, Packet fwdPacket) {
+        this.delay = delay;
+        this.forwardedPacket = fwdPacket;
+    }
+
+    @Override
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    @Override
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    @Override
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"")
+                .append(getNamespace()).append("\">");
+
+        if (delay != null)
+            buf.append(delay.toXML());
+        buf.append(forwardedPacket.toXML());
+
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * get the packet forwarded by this stanza.
+     *
+     * @return the {@link Packet} instance (typically a message) that was forwarded.
+     */
+    public Packet getForwardedPacket() {
+        return forwardedPacket;
+    }
+
+    /**
+     * get the timestamp of the forwarded packet.
+     *
+     * @return the {@link DelayInfo} representing the time when the original packet was sent. May be null.
+     */
+    public DelayInfo getDelayInfo() {
+        return delay;
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+        DelayInfoProvider dip = new DelayInfoProvider();
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            DelayInfo di = null;
+            Packet packet = null;
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("delay"))
+                        di = (DelayInfo)dip.parseExtension(parser);
+                    else if (parser.getName().equals("message"))
+                        packet = PacketParserUtils.parseMessage(parser);
+                    else throw new Exception("Unsupported forwarded packet type: " + parser.getName());
+                }
+                else if (eventType == XmlPullParser.END_TAG && parser.getName().equals(ELEMENT_NAME))
+                    done = true;
+            }
+            if (packet == null)
+                throw new Exception("forwarded extension must contain a packet");
+            return new Forwarded(di, packet);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/Affiliate.java b/src/org/jivesoftware/smackx/muc/Affiliate.java
new file mode 100644
index 0000000..09a04f6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/Affiliate.java
@@ -0,0 +1,98 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smackx.packet.MUCAdmin;
+import org.jivesoftware.smackx.packet.MUCOwner;
+
+/**
+ * Represents an affiliation of a user to a given room. The affiliate's information will always have
+ * the bare jid of the real user and its affiliation. If the affiliate is an occupant of the room
+ * then we will also have information about the role and nickname of the user in the room.
+ *
+ * @author Gaston Dombiak
+ */
+public class Affiliate {
+    // Fields that must have a value
+    private String jid;
+    private String affiliation;
+
+    // Fields that may have a value
+    private String role;
+    private String nick;
+
+    Affiliate(MUCOwner.Item item) {
+        super();
+        this.jid = item.getJid();
+        this.affiliation = item.getAffiliation();
+        this.role = item.getRole();
+        this.nick = item.getNick();
+    }
+
+    Affiliate(MUCAdmin.Item item) {
+        super();
+        this.jid = item.getJid();
+        this.affiliation = item.getAffiliation();
+        this.role = item.getRole();
+        this.nick = item.getNick();
+    }
+
+    /**
+     * Returns the bare JID of the affiliated user. This information will always be available.
+     *
+     * @return the bare JID of the affiliated user.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Returns the affiliation of the afffiliated user. Possible affiliations are: "owner", "admin",
+     * "member", "outcast". This information will always be available.
+     *
+     * @return the affiliation of the afffiliated user.
+     */
+    public String getAffiliation() {
+        return affiliation;
+    }
+
+    /**
+     * Returns the current role of the affiliated user if the user is currently in the room.
+     * If the user is not present in the room then the answer will be null.
+     *
+     * @return the current role of the affiliated user in the room or null if the user is not in
+     *         the room.
+     */
+    public String getRole() {
+        return role;
+    }
+
+    /**
+     * Returns the current nickname of the affiliated user if the user is currently in the room.
+     * If the user is not present in the room then the answer will be null.
+     *
+     * @return the current nickname of the affiliated user in the room or null if the user is not in
+     *         the room.
+     */
+    public String getNick() {
+        return nick;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/ConnectionDetachedPacketCollector.java b/src/org/jivesoftware/smackx/muc/ConnectionDetachedPacketCollector.java
new file mode 100644
index 0000000..243c298
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/ConnectionDetachedPacketCollector.java
@@ -0,0 +1,123 @@
+/**
+ * $RCSfile$
+ * $Revision: 2779 $
+ * $Date: 2005-09-05 17:00:45 -0300 (Mon, 05 Sep 2005) $
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import java.util.concurrent.ArrayBlockingQueue;
+import java.util.concurrent.TimeUnit;
+
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * A variant of the {@link org.jivesoftware.smack.PacketCollector} class
+ * that does not force attachment to a <code>Connection</code>
+ * on creation and no filter is required. Used to collect message
+ * packets targeted to a group chat room.
+ *
+ * @author Larry Kirschner
+ */
+class ConnectionDetachedPacketCollector {
+    /**
+     * Max number of packets that any one collector can hold. After the max is
+     * reached, older packets will be automatically dropped from the queue as
+     * new packets are added.
+     */
+    private int maxPackets = SmackConfiguration.getPacketCollectorSize();
+
+    private ArrayBlockingQueue<Packet> resultQueue;
+
+    /**
+     * Creates a new packet collector. If the packet filter is <tt>null</tt>, then
+     * all packets will match this collector.
+     */
+    public ConnectionDetachedPacketCollector() {
+        this(SmackConfiguration.getPacketCollectorSize());
+    }
+
+    /**
+     * Creates a new packet collector. If the packet filter is <tt>null</tt>, then
+     * all packets will match this collector.
+     */
+    public ConnectionDetachedPacketCollector(int maxSize) {
+        this.resultQueue = new ArrayBlockingQueue<Packet>(maxSize);
+    }
+
+    /**
+     * Polls to see if a packet is currently available and returns it, or
+     * immediately returns <tt>null</tt> if no packets are currently in the
+     * result queue.
+     *
+     * @return the next packet result, or <tt>null</tt> if there are no more
+     *      results.
+     */
+    public Packet pollResult() {
+    	return resultQueue.poll();
+    }
+
+    /**
+     * Returns the next available packet. The method call will block (not return)
+     * until a packet is available.
+     *
+     * @return the next available packet.
+     */
+    public Packet nextResult() {
+        try {
+			return resultQueue.take();
+		}
+		catch (InterruptedException e) {
+			throw new RuntimeException(e);
+		}
+    }
+
+    /**
+     * Returns the next available packet. The method call will block (not return)
+     * until a packet is available or the <tt>timeout</tt> has elapased. If the
+     * timeout elapses without a result, <tt>null</tt> will be returned.
+     *
+     * @param timeout the amount of time to wait for the next packet (in milleseconds).
+     * @return the next available packet.
+     */
+    public Packet nextResult(long timeout) {
+        try {
+        	return resultQueue.poll(timeout, TimeUnit.MILLISECONDS);
+		}
+		catch (InterruptedException e) {
+			throw new RuntimeException(e);
+		}
+    }
+
+    /**
+     * Processes a packet to see if it meets the criteria for this packet collector.
+     * If so, the packet is added to the result queue.
+     *
+     * @param packet the packet to process.
+     */
+    protected void processPacket(Packet packet) {
+        if (packet == null) {
+            return;
+        }
+        
+    	while (!resultQueue.offer(packet)) {
+    		// Since we know the queue is full, this poll should never actually block.
+    		resultQueue.poll();
+    	}
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/DeafOccupantInterceptor.java b/src/org/jivesoftware/smackx/muc/DeafOccupantInterceptor.java
new file mode 100644
index 0000000..24570fd
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/DeafOccupantInterceptor.java
@@ -0,0 +1,76 @@
+/**
+ * $RCSfile$
+ * $Revision:  $
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smack.PacketInterceptor;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.Presence;
+
+/**
+ * Packet interceptor that will intercept presence packets sent to the MUC service to indicate
+ * that the user wants to be a deaf occupant. A user can only indicate that he wants to be a
+ * deaf occupant while joining the room. It is not possible to become deaf or stop being deaf
+ * after the user joined the room.<p>
+ *
+ * Deaf occupants will not get messages broadcasted to all room occupants. However, they will
+ * be able to get private messages, presences, IQ packets or room history. To use this
+ * functionality you will need to send the message
+ * {@link MultiUserChat#addPresenceInterceptor(org.jivesoftware.smack.PacketInterceptor)} and
+ * pass this interceptor as the parameter.<p>
+ *
+ * Note that this is a custom extension to the MUC service so it may not work with other servers
+ * than Wildfire.
+ *
+ * @author Gaston Dombiak
+ */
+public class DeafOccupantInterceptor implements PacketInterceptor {
+
+    public void interceptPacket(Packet packet) {
+        Presence presence = (Presence) packet;
+        // Check if user is joining a room
+        if (Presence.Type.available == presence.getType() &&
+                presence.getExtension("x", "http://jabber.org/protocol/muc") != null) {
+            // Add extension that indicates that user wants to be a deaf occupant
+            packet.addExtension(new DeafExtension());
+        }
+    }
+
+    private static class DeafExtension implements PacketExtension {
+
+        public String getElementName() {
+            return "x";
+        }
+
+        public String getNamespace() {
+            return "http://jivesoftware.org/protocol/muc";
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace())
+                    .append("\">");
+            buf.append("<deaf-occupant/>");
+            buf.append("</").append(getElementName()).append(">");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/DefaultParticipantStatusListener.java b/src/org/jivesoftware/smackx/muc/DefaultParticipantStatusListener.java
new file mode 100644
index 0000000..6eb9efa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/DefaultParticipantStatusListener.java
@@ -0,0 +1,79 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * Default implementation of the ParticipantStatusListener interface.<p>
+ *
+ * This class does not provide any behavior by default. It just avoids having
+ * to implement all the inteface methods if the user is only interested in implementing
+ * some of the methods.
+ * 
+ * @author Gaston Dombiak
+ */
+public class DefaultParticipantStatusListener implements ParticipantStatusListener {
+
+    public void joined(String participant) {
+    }
+
+    public void left(String participant) {
+    }
+
+    public void kicked(String participant, String actor, String reason) {
+    }
+
+    public void voiceGranted(String participant) {
+    }
+
+    public void voiceRevoked(String participant) {
+    }
+
+    public void banned(String participant, String actor, String reason) {
+    }
+
+    public void membershipGranted(String participant) {
+    }
+
+    public void membershipRevoked(String participant) {
+    }
+
+    public void moderatorGranted(String participant) {
+    }
+
+    public void moderatorRevoked(String participant) {
+    }
+
+    public void ownershipGranted(String participant) {
+    }
+
+    public void ownershipRevoked(String participant) {
+    }
+
+    public void adminGranted(String participant) {
+    }
+
+    public void adminRevoked(String participant) {
+    }
+
+    public void nicknameChanged(String participant, String newNickname) {
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/DefaultUserStatusListener.java b/src/org/jivesoftware/smackx/muc/DefaultUserStatusListener.java
new file mode 100644
index 0000000..de7cc87
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/DefaultUserStatusListener.java
@@ -0,0 +1,70 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * Default implementation of the UserStatusListener interface.<p>
+ *
+ * This class does not provide any behavior by default. It just avoids having
+ * to implement all the inteface methods if the user is only interested in implementing
+ * some of the methods.
+ * 
+ * @author Gaston Dombiak
+ */
+public class DefaultUserStatusListener implements UserStatusListener {
+
+    public void kicked(String actor, String reason) {
+    }
+
+    public void voiceGranted() {
+    }
+
+    public void voiceRevoked() {
+    }
+
+    public void banned(String actor, String reason) {
+    }
+
+    public void membershipGranted() {
+    }
+
+    public void membershipRevoked() {
+    }
+
+    public void moderatorGranted() {
+    }
+
+    public void moderatorRevoked() {
+    }
+
+    public void ownershipGranted() {
+    }
+
+    public void ownershipRevoked() {
+    }
+
+    public void adminGranted() {
+    }
+
+    public void adminRevoked() {
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/DiscussionHistory.java b/src/org/jivesoftware/smackx/muc/DiscussionHistory.java
new file mode 100644
index 0000000..036f6cb
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/DiscussionHistory.java
@@ -0,0 +1,173 @@
+/**
+ * $RCSfile$
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import java.util.Date;
+
+import org.jivesoftware.smackx.packet.MUCInitialPresence;
+
+/**
+ * The DiscussionHistory class controls the number of characters or messages to receive
+ * when entering a room. The room will decide the amount of history to return if you don't 
+ * specify a DiscussionHistory while joining a room.<p>
+ * 
+ * You can use some or all of these variable to control the amount of history to receive:   
+ * <ul>
+ *  <li>maxchars -> total number of characters to receive in the history.
+ *  <li>maxstanzas -> total number of messages to receive in the history.
+ *  <li>seconds -> only the messages received in the last "X" seconds will be included in the 
+ * history.
+ *  <li>since -> only the messages received since the datetime specified will be included in 
+ * the history.
+ * </ul>
+ * 
+ * Note: Setting maxchars to 0 indicates that the user requests to receive no history.
+ * 
+ * @author Gaston Dombiak
+ */
+public class DiscussionHistory {
+
+    private int maxChars = -1;
+    private int maxStanzas = -1;
+    private int seconds = -1;
+    private Date since;
+
+    /**
+     * Returns the total number of characters to receive in the history.
+     * 
+     * @return total number of characters to receive in the history.
+     */
+    public int getMaxChars() {
+        return maxChars;
+    }
+
+    /**
+     * Returns the total number of messages to receive in the history.
+     * 
+     * @return the total number of messages to receive in the history.
+     */
+    public int getMaxStanzas() {
+        return maxStanzas;
+    }
+
+    /**
+     * Returns the number of seconds to use to filter the messages received during that time. 
+     * In other words, only the messages received in the last "X" seconds will be included in 
+     * the history.
+     * 
+     * @return the number of seconds to use to filter the messages received during that time.
+     */
+    public int getSeconds() {
+        return seconds;
+    }
+
+    /**
+     * Returns the since date to use to filter the messages received during that time. 
+     * In other words, only the messages received since the datetime specified will be 
+     * included in the history.
+     * 
+     * @return the since date to use to filter the messages received during that time.
+     */
+    public Date getSince() {
+        return since;
+    }
+
+    /**
+     * Sets the total number of characters to receive in the history.
+     * 
+     * @param maxChars the total number of characters to receive in the history.
+     */
+    public void setMaxChars(int maxChars) {
+        this.maxChars = maxChars;
+    }
+
+    /**
+     * Sets the total number of messages to receive in the history.
+     * 
+     * @param maxStanzas the total number of messages to receive in the history.
+     */
+    public void setMaxStanzas(int maxStanzas) {
+        this.maxStanzas = maxStanzas;
+    }
+
+    /**
+     * Sets the number of seconds to use to filter the messages received during that time. 
+     * In other words, only the messages received in the last "X" seconds will be included in 
+     * the history.
+     * 
+     * @param seconds the number of seconds to use to filter the messages received during 
+     * that time.
+     */
+    public void setSeconds(int seconds) {
+        this.seconds = seconds;
+    }
+
+    /**
+     * Sets the since date to use to filter the messages received during that time. 
+     * In other words, only the messages received since the datetime specified will be 
+     * included in the history.
+     * 
+     * @param since the since date to use to filter the messages received during that time.
+     */
+    public void setSince(Date since) {
+        this.since = since;
+    }
+
+    /**
+     * Returns true if the history has been configured with some values.
+     * 
+     * @return true if the history has been configured with some values.
+     */
+    private boolean isConfigured() {
+        return maxChars > -1 || maxStanzas > -1 || seconds > -1 || since != null;
+    }
+
+    /**
+     * Returns the History that manages the amount of discussion history provided on entering a 
+     * room.
+     * 
+     * @return the History that manages the amount of discussion history provided on entering a 
+     * room.
+     */
+    MUCInitialPresence.History getMUCHistory() {
+        // Return null if the history was not properly configured  
+        if (!isConfigured()) {
+            return null;
+        }
+        
+        MUCInitialPresence.History mucHistory = new MUCInitialPresence.History();
+        if (maxChars > -1) {
+            mucHistory.setMaxChars(maxChars);
+        }
+        if (maxStanzas > -1) {
+            mucHistory.setMaxStanzas(maxStanzas);
+        }
+        if (seconds > -1) {
+            mucHistory.setSeconds(seconds);
+        }
+        if (since != null) {
+            mucHistory.setSince(since);
+        }
+        return mucHistory;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/HostedRoom.java b/src/org/jivesoftware/smackx/muc/HostedRoom.java
new file mode 100644
index 0000000..7cd580b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/HostedRoom.java
@@ -0,0 +1,65 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smackx.packet.DiscoverItems;
+
+/**
+ * Hosted rooms by a chat service may be discovered if they are configured to appear in the room
+ * directory . The information that may be discovered is the XMPP address of the room and the room
+ * name. The address of the room may be used for obtaining more detailed information
+ * {@link org.jivesoftware.smackx.muc.MultiUserChat#getRoomInfo(org.jivesoftware.smack.Connection, String)}
+ * or could be used for joining the room
+ * {@link org.jivesoftware.smackx.muc.MultiUserChat#MultiUserChat(org.jivesoftware.smack.Connection, String)}
+ * and {@link org.jivesoftware.smackx.muc.MultiUserChat#join(String)}.
+ *
+ * @author Gaston Dombiak
+ */
+public class HostedRoom {
+
+    private String jid;
+
+    private String name;
+
+    public HostedRoom(DiscoverItems.Item item) {
+        super();
+        jid = item.getEntityID();
+        name = item.getName();
+    }
+
+    /**
+     * Returns the XMPP address of the hosted room by the chat service. This address may be used
+     * when creating a <code>MultiUserChat</code> when joining a room.
+     *
+     * @return the XMPP address of the hosted room by the chat service.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Returns the name of the room.
+     *
+     * @return the name of the room.
+     */
+    public String getName() {
+        return name;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/InvitationListener.java b/src/org/jivesoftware/smackx/muc/InvitationListener.java
new file mode 100644
index 0000000..34c915d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/InvitationListener.java
@@ -0,0 +1,49 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.Message;
+
+/**
+ * A listener that is fired anytime an invitation to join a MUC room is received.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface InvitationListener {
+
+    /**
+     * Called when the an invitation to join a MUC room is received.<p>
+     * 
+     * If the room is password-protected, the invitee will receive a password to use to join
+     * the room. If the room is members-only, the the invitee may be added to the member list.
+     * 
+     * @param conn the Connection that received the invitation.
+     * @param room the room that invitation refers to.
+     * @param inviter the inviter that sent the invitation. (e.g. crone1@shakespeare.lit).
+     * @param reason the reason why the inviter sent the invitation.
+     * @param password the password to use when joining the room.
+     * @param message the message used by the inviter to send the invitation.
+     */
+    public abstract void invitationReceived(Connection conn, String room, String inviter, String reason,
+                                            String password, Message message);
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/InvitationRejectionListener.java b/src/org/jivesoftware/smackx/muc/InvitationRejectionListener.java
new file mode 100644
index 0000000..1580c6f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/InvitationRejectionListener.java
@@ -0,0 +1,38 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * A listener that is fired anytime an invitee declines or rejects an invitation.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface InvitationRejectionListener {
+
+    /**
+     * Called when the invitee declines the invitation.
+     * 
+     * @param invitee the invitee that declined the invitation. (e.g. hecate@shakespeare.lit).
+     * @param reason the reason why the invitee declined the invitation.
+     */
+    public abstract void invitationDeclined(String invitee, String reason);
+    
+}
diff --git a/src/org/jivesoftware/smackx/muc/MultiUserChat.java b/src/org/jivesoftware/smackx/muc/MultiUserChat.java
new file mode 100644
index 0000000..9a46444
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/MultiUserChat.java
@@ -0,0 +1,2743 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import java.lang.ref.WeakReference;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.Chat;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.MessageListener;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.PacketInterceptor;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.AndFilter;
+import org.jivesoftware.smack.filter.FromMatchesFilter;
+import org.jivesoftware.smack.filter.MessageTypeFilter;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.packet.Registration;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.NodeInformationProvider;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.packet.MUCAdmin;
+import org.jivesoftware.smackx.packet.MUCInitialPresence;
+import org.jivesoftware.smackx.packet.MUCOwner;
+import org.jivesoftware.smackx.packet.MUCUser;
+
+/**
+ * A MultiUserChat is a conversation that takes place among many users in a virtual
+ * room. A room could have many occupants with different affiliation and roles.
+ * Possible affiliatons are "owner", "admin", "member", and "outcast". Possible roles
+ * are "moderator", "participant", and "visitor". Each role and affiliation guarantees
+ * different privileges (e.g. Send messages to all occupants, Kick participants and visitors,
+ * Grant voice, Edit member list, etc.).
+ *
+ * @author Gaston Dombiak, Larry Kirschner
+ */
+public class MultiUserChat {
+
+    private final static String discoNamespace = "http://jabber.org/protocol/muc";
+    private final static String discoNode = "http://jabber.org/protocol/muc#rooms";
+
+    private static Map<Connection, List<String>> joinedRooms =
+            new WeakHashMap<Connection, List<String>>();
+
+    private Connection connection;
+    private String room;
+    private String subject;
+    private String nickname = null;
+    private boolean joined = false;
+    private Map<String, Presence> occupantsMap = new ConcurrentHashMap<String, Presence>();
+
+    private final List<InvitationRejectionListener> invitationRejectionListeners =
+            new ArrayList<InvitationRejectionListener>();
+    private final List<SubjectUpdatedListener> subjectUpdatedListeners =
+            new ArrayList<SubjectUpdatedListener>();
+    private final List<UserStatusListener> userStatusListeners =
+            new ArrayList<UserStatusListener>();
+    private final List<ParticipantStatusListener> participantStatusListeners =
+            new ArrayList<ParticipantStatusListener>();
+
+    private PacketFilter presenceFilter;
+    private List<PacketInterceptor> presenceInterceptors = new ArrayList<PacketInterceptor>();
+    private PacketFilter messageFilter;
+    private RoomListenerMultiplexor roomListenerMultiplexor;
+    private ConnectionDetachedPacketCollector messageCollector;
+    private List<PacketListener> connectionListeners = new ArrayList<PacketListener>();
+
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(final Connection connection) {
+                // Set on every established connection that this client supports the Multi-User
+                // Chat protocol. This information will be used when another client tries to
+                // discover whether this client supports MUC or not.
+                ServiceDiscoveryManager.getInstanceFor(connection).addFeature(discoNamespace);
+                // Set the NodeInformationProvider that will provide information about the
+                // joined rooms whenever a disco request is received
+                ServiceDiscoveryManager.getInstanceFor(connection).setNodeInformationProvider(
+                    discoNode,
+                    new NodeInformationProvider() {
+                        public List<DiscoverItems.Item> getNodeItems() {
+                            List<DiscoverItems.Item> answer = new ArrayList<DiscoverItems.Item>();
+                            Iterator<String> rooms=MultiUserChat.getJoinedRooms(connection);
+                            while (rooms.hasNext()) {
+                                answer.add(new DiscoverItems.Item(rooms.next()));
+                            }
+                            return answer;
+                        }
+
+                        public List<String> getNodeFeatures() {
+                            return null;
+                        }
+
+                        public List<DiscoverInfo.Identity> getNodeIdentities() {
+                            return null;
+                        }
+
+                        @Override
+                        public List<PacketExtension> getNodePacketExtensions() {
+                            return null;
+                        }
+                    });
+            }
+        });
+    }
+
+    /**
+     * Creates a new multi user chat with the specified connection and room name. Note: no
+     * information is sent to or received from the server until you attempt to
+     * {@link #join(String) join} the chat room. On some server implementations,
+     * the room will not be created until the first person joins it.<p>
+     *
+     * Most XMPP servers use a sub-domain for the chat service (eg chat.example.com
+     * for the XMPP server example.com). You must ensure that the room address you're
+     * trying to connect to includes the proper chat sub-domain.
+     *
+     * @param connection the XMPP connection.
+     * @param room the name of the room in the form "roomName@service", where
+     *      "service" is the hostname at which the multi-user chat
+     *      service is running. Make sure to provide a valid JID.
+     */
+    public MultiUserChat(Connection connection, String room) {
+        this.connection = connection;
+        this.room = room.toLowerCase();
+        init();
+    }
+
+    /**
+     * Returns true if the specified user supports the Multi-User Chat protocol.
+     *
+     * @param connection the connection to use to perform the service discovery.
+     * @param user the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com.
+     * @return a boolean indicating whether the specified user supports the MUC protocol.
+     */
+    public static boolean isServiceEnabled(Connection connection, String user) {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(user);
+            return result.containsFeature(discoNamespace);
+        }
+        catch (XMPPException e) {
+            e.printStackTrace();
+            return false;
+        }
+    }
+
+    /**
+     * Returns an Iterator on the rooms where the user has joined using a given connection.
+     * The Iterator will contain Strings where each String represents a room
+     * (e.g. room@muc.jabber.org).
+     *
+     * @param connection the connection used to join the rooms.
+     * @return an Iterator on the rooms where the user has joined using a given connection.
+     */
+    private static Iterator<String> getJoinedRooms(Connection connection) {
+        List<String> rooms = joinedRooms.get(connection);
+        if (rooms != null) {
+            return rooms.iterator();
+        }
+        // Return an iterator on an empty collection (i.e. the user never joined a room)
+        return new ArrayList<String>().iterator();
+    }
+
+    /**
+     * Returns an Iterator on the rooms where the requested user has joined. The Iterator will
+     * contain Strings where each String represents a room (e.g. room@muc.jabber.org).
+     *
+     * @param connection the connection to use to perform the service discovery.
+     * @param user the user to check. A fully qualified xmpp ID, e.g. jdoe@example.com.
+     * @return an Iterator on the rooms where the requested user has joined.
+     */
+    public static Iterator<String> getJoinedRooms(Connection connection, String user) {
+        try {
+            ArrayList<String> answer = new ArrayList<String>();
+            // Send the disco packet to the user
+            DiscoverItems result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverItems(user, discoNode);
+            // Collect the entityID for each returned item
+            for (Iterator<DiscoverItems.Item> items=result.getItems(); items.hasNext();) {
+                answer.add(items.next().getEntityID());
+            }
+            return answer.iterator();
+        }
+        catch (XMPPException e) {
+            e.printStackTrace();
+            // Return an iterator on an empty collection
+            return new ArrayList<String>().iterator();
+        }
+    }
+
+    /**
+     * Returns the discovered information of a given room without actually having to join the room.
+     * The server will provide information only for rooms that are public.
+     *
+     * @param connection the XMPP connection to use for discovering information about the room.
+     * @param room the name of the room in the form "roomName@service" of which we want to discover
+     *        its information.
+     * @return the discovered information of a given room without actually having to join the room.
+     * @throws XMPPException if an error occured while trying to discover information of a room.
+     */
+    public static RoomInfo getRoomInfo(Connection connection, String room)
+            throws XMPPException {
+        DiscoverInfo info = ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(room);
+        return new RoomInfo(info);
+    }
+
+    /**
+     * Returns a collection with the XMPP addresses of the Multi-User Chat services.
+     *
+     * @param connection the XMPP connection to use for discovering Multi-User Chat services.
+     * @return a collection with the XMPP addresses of the Multi-User Chat services.
+     * @throws XMPPException if an error occured while trying to discover MUC services.
+     */
+    public static Collection<String> getServiceNames(Connection connection) throws XMPPException {
+        final List<String> answer = new ArrayList<String>();
+        ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection);
+        DiscoverItems items = discoManager.discoverItems(connection.getServiceName());
+        for (Iterator<DiscoverItems.Item> it = items.getItems(); it.hasNext();) {
+            DiscoverItems.Item item = it.next();
+            try {
+                DiscoverInfo info = discoManager.discoverInfo(item.getEntityID());
+                if (info.containsFeature("http://jabber.org/protocol/muc")) {
+                    answer.add(item.getEntityID());
+                }
+            }
+            catch (XMPPException e) {
+                // Trouble finding info in some cases. This is a workaround for
+                // discovering info on remote servers.
+            }
+        }
+        return answer;
+    }
+
+    /**
+     * Returns a collection of HostedRooms where each HostedRoom has the XMPP address of the room
+     * and the room's name. Once discovered the rooms hosted by a chat service it is possible to
+     * discover more detailed room information or join the room.
+     *
+     * @param connection the XMPP connection to use for discovering hosted rooms by the MUC service.
+     * @param serviceName the service that is hosting the rooms to discover.
+     * @return a collection of HostedRooms.
+     * @throws XMPPException if an error occured while trying to discover the information.
+     */
+    public static Collection<HostedRoom> getHostedRooms(Connection connection, String serviceName)
+            throws XMPPException {
+        List<HostedRoom> answer = new ArrayList<HostedRoom>();
+        ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection);
+        DiscoverItems items = discoManager.discoverItems(serviceName);
+        for (Iterator<DiscoverItems.Item> it = items.getItems(); it.hasNext();) {
+            answer.add(new HostedRoom(it.next()));
+        }
+        return answer;
+    }
+
+    /**
+     * Returns the name of the room this MultiUserChat object represents.
+     *
+     * @return the multi user chat room name.
+     */
+    public String getRoom() {
+        return room;
+    }
+
+    /**
+     * Creates the room according to some default configuration, assign the requesting user
+     * as the room owner, and add the owner to the room but not allow anyone else to enter
+     * the room (effectively "locking" the room). The requesting user will join the room
+     * under the specified nickname as soon as the room has been created.<p>
+     *
+     * To create an "Instant Room", that means a room with some default configuration that is
+     * available for immediate access, the room's owner should send an empty form after creating
+     * the room. {@link #sendConfigurationForm(Form)}<p>
+     *
+     * To create a "Reserved Room", that means a room manually configured by the room creator
+     * before anyone is allowed to enter, the room's owner should complete and send a form after
+     * creating the room. Once the completed configutation form is sent to the server, the server
+     * will unlock the room. {@link #sendConfigurationForm(Form)}
+     *
+     * @param nickname the nickname to use.
+     * @throws XMPPException if the room couldn't be created for some reason
+     *          (e.g. room already exists; user already joined to an existant room or
+     *          405 error if the user is not allowed to create the room)
+     */
+    public synchronized void create(String nickname) throws XMPPException {
+        if (nickname == null || nickname.equals("")) {
+            throw new IllegalArgumentException("Nickname must not be null or blank.");
+        }
+        // If we've already joined the room, leave it before joining under a new
+        // nickname.
+        if (joined) {
+            throw new IllegalStateException("Creation failed - User already joined the room.");
+        }
+        // We create a room by sending a presence packet to room@service/nick
+        // and signal support for MUC. The owner will be automatically logged into the room.
+        Presence joinPresence = new Presence(Presence.Type.available);
+        joinPresence.setTo(room + "/" + nickname);
+        // Indicate the the client supports MUC
+        joinPresence.addExtension(new MUCInitialPresence());
+        // Invoke presence interceptors so that extra information can be dynamically added
+        for (PacketInterceptor packetInterceptor : presenceInterceptors) {
+            packetInterceptor.interceptPacket(joinPresence);
+        }
+
+        // Wait for a presence packet back from the server.
+        PacketFilter responseFilter =
+            new AndFilter(
+                new FromMatchesFilter(room + "/" + nickname),
+                new PacketTypeFilter(Presence.class));
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send create & join packet.
+        connection.sendPacket(joinPresence);
+        // Wait up to a certain number of seconds for a reply.
+        Presence presence =
+            (Presence) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (presence == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (presence.getError() != null) {
+            throw new XMPPException(presence.getError());
+        }
+        // Whether the room existed before or was created, the user has joined the room
+        this.nickname = nickname;
+        joined = true;
+        userHasJoined();
+
+        // Look for confirmation of room creation from the server
+        MUCUser mucUser = getMUCUserExtension(presence);
+        if (mucUser != null && mucUser.getStatus() != null) {
+            if ("201".equals(mucUser.getStatus().getCode())) {
+                // Room was created and the user has joined the room
+                return;
+            }
+        }
+        // We need to leave the room since it seems that the room already existed
+        leave();
+        throw new XMPPException("Creation failed - Missing acknowledge of room creation.");
+    }
+
+    /**
+     * Joins the chat room using the specified nickname. If already joined
+     * using another nickname, this method will first leave the room and then
+     * re-join using the new nickname. The default timeout of Smack for a reply
+     * from the group chat server that the join succeeded will be used. After
+     * joining the room, the room will decide the amount of history to send.
+     *
+     * @param nickname the nickname to use.
+     * @throws XMPPException if an error occurs joining the room. In particular, a
+     *      401 error can occur if no password was provided and one is required; or a
+     *      403 error can occur if the user is banned; or a
+     *      404 error can occur if the room does not exist or is locked; or a
+     *      407 error can occur if user is not on the member list; or a
+     *      409 error can occur if someone is already in the group chat with the same nickname.
+     */
+    public void join(String nickname) throws XMPPException {
+        join(nickname, null, null, SmackConfiguration.getPacketReplyTimeout());
+    }
+
+    /**
+     * Joins the chat room using the specified nickname and password. If already joined
+     * using another nickname, this method will first leave the room and then
+     * re-join using the new nickname. The default timeout of Smack for a reply
+     * from the group chat server that the join succeeded will be used. After
+     * joining the room, the room will decide the amount of history to send.<p>
+     *
+     * A password is required when joining password protected rooms. If the room does
+     * not require a password there is no need to provide one.
+     *
+     * @param nickname the nickname to use.
+     * @param password the password to use.
+     * @throws XMPPException if an error occurs joining the room. In particular, a
+     *      401 error can occur if no password was provided and one is required; or a
+     *      403 error can occur if the user is banned; or a
+     *      404 error can occur if the room does not exist or is locked; or a
+     *      407 error can occur if user is not on the member list; or a
+     *      409 error can occur if someone is already in the group chat with the same nickname.
+     */
+    public void join(String nickname, String password) throws XMPPException {
+        join(nickname, password, null, SmackConfiguration.getPacketReplyTimeout());
+    }
+
+    /**
+     * Joins the chat room using the specified nickname and password. If already joined
+     * using another nickname, this method will first leave the room and then
+     * re-join using the new nickname.<p>
+     *
+     * To control the amount of history to receive while joining a room you will need to provide
+     * a configured DiscussionHistory object.<p>
+     *
+     * A password is required when joining password protected rooms. If the room does
+     * not require a password there is no need to provide one.<p>
+     *
+     * If the room does not already exist when the user seeks to enter it, the server will
+     * decide to create a new room or not.
+     *
+     * @param nickname the nickname to use.
+     * @param password the password to use.
+     * @param history the amount of discussion history to receive while joining a room.
+     * @param timeout the amount of time to wait for a reply from the MUC service(in milleseconds).
+     * @throws XMPPException if an error occurs joining the room. In particular, a
+     *      401 error can occur if no password was provided and one is required; or a
+     *      403 error can occur if the user is banned; or a
+     *      404 error can occur if the room does not exist or is locked; or a
+     *      407 error can occur if user is not on the member list; or a
+     *      409 error can occur if someone is already in the group chat with the same nickname.
+     */
+    public synchronized void join(
+        String nickname,
+        String password,
+        DiscussionHistory history,
+        long timeout)
+        throws XMPPException {
+        if (nickname == null || nickname.equals("")) {
+            throw new IllegalArgumentException("Nickname must not be null or blank.");
+        }
+        // If we've already joined the room, leave it before joining under a new
+        // nickname.
+        if (joined) {
+            leave();
+        }
+        // We join a room by sending a presence packet where the "to"
+        // field is in the form "roomName@service/nickname"
+        Presence joinPresence = new Presence(Presence.Type.available);
+        joinPresence.setTo(room + "/" + nickname);
+
+        // Indicate the the client supports MUC
+        MUCInitialPresence mucInitialPresence = new MUCInitialPresence();
+        if (password != null) {
+            mucInitialPresence.setPassword(password);
+        }
+        if (history != null) {
+            mucInitialPresence.setHistory(history.getMUCHistory());
+        }
+        joinPresence.addExtension(mucInitialPresence);
+        // Invoke presence interceptors so that extra information can be dynamically added
+        for (PacketInterceptor packetInterceptor : presenceInterceptors) {
+            packetInterceptor.interceptPacket(joinPresence);
+        }
+
+        // Wait for a presence packet back from the server.
+        PacketFilter responseFilter =
+                new AndFilter(
+                        new FromMatchesFilter(room + "/" + nickname),
+                        new PacketTypeFilter(Presence.class));
+        PacketCollector response = null;
+        Presence presence;
+        try {
+            response = connection.createPacketCollector(responseFilter);
+            // Send join packet.
+            connection.sendPacket(joinPresence);
+            // Wait up to a certain number of seconds for a reply.
+            presence = (Presence) response.nextResult(timeout);
+        }
+        finally {
+            // Stop queuing results
+            if (response != null) {
+                response.cancel();
+            }
+        }
+
+        if (presence == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (presence.getError() != null) {
+            throw new XMPPException(presence.getError());
+        }
+        this.nickname = nickname;
+        joined = true;
+        userHasJoined();
+    }
+
+    /**
+     * Returns true if currently in the multi user chat (after calling the {@link
+     * #join(String)} method).
+     *
+     * @return true if currently in the multi user chat room.
+     */
+    public boolean isJoined() {
+        return joined;
+    }
+
+    /**
+     * Leave the chat room.
+     */
+    public synchronized void leave() {
+        // If not joined already, do nothing.
+        if (!joined) {
+            return;
+        }
+        // We leave a room by sending a presence packet where the "to"
+        // field is in the form "roomName@service/nickname"
+        Presence leavePresence = new Presence(Presence.Type.unavailable);
+        leavePresence.setTo(room + "/" + nickname);
+        // Invoke presence interceptors so that extra information can be dynamically added
+        for (PacketInterceptor packetInterceptor : presenceInterceptors) {
+            packetInterceptor.interceptPacket(leavePresence);
+        }
+        connection.sendPacket(leavePresence);
+        // Reset occupant information.
+        occupantsMap.clear();
+        nickname = null;
+        joined = false;
+        userHasLeft();
+    }
+
+    /**
+     * Returns the room's configuration form that the room's owner can use or <tt>null</tt> if
+     * no configuration is possible. The configuration form allows to set the room's language,
+     * enable logging, specify room's type, etc..
+     *
+     * @return the Form that contains the fields to complete together with the instrucions or
+     * <tt>null</tt> if no configuration is possible.
+     * @throws XMPPException if an error occurs asking the configuration form for the room.
+     */
+    public Form getConfigurationForm() throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.GET);
+
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Request the configuration form to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+        return Form.getFormFrom(answer);
+    }
+
+    /**
+     * Sends the completed configuration form to the server. The room will be configured
+     * with the new settings defined in the form. If the form is empty then the server
+     * will create an instant room (will use default configuration).
+     *
+     * @param form the form with the new settings.
+     * @throws XMPPException if an error occurs setting the new rooms' configuration.
+     */
+    public void sendConfigurationForm(Form form) throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        iq.addExtension(form.getDataFormToSend());
+
+        // Filter packets looking for an answer from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the completed configuration form to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    /**
+     * Returns the room's registration form that an unaffiliated user, can use to become a member
+     * of the room or <tt>null</tt> if no registration is possible. Some rooms may restrict the
+     * privilege to register members and allow only room admins to add new members.<p>
+     *
+     * If the user requesting registration requirements is not allowed to register with the room
+     * (e.g. because that privilege has been restricted), the room will return a "Not Allowed"
+     * error to the user (error code 405).
+     *
+     * @return the registration Form that contains the fields to complete together with the
+     * instrucions or <tt>null</tt> if no registration is possible.
+     * @throws XMPPException if an error occurs asking the registration form for the room or a
+     * 405 error if the user is not allowed to register with the room.
+     */
+    public Form getRegistrationForm() throws XMPPException {
+        Registration reg = new Registration();
+        reg.setType(IQ.Type.GET);
+        reg.setTo(room);
+
+        PacketFilter filter =
+            new AndFilter(new PacketIDFilter(reg.getPacketID()), new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+        return Form.getFormFrom(result);
+    }
+
+    /**
+     * Sends the completed registration form to the server. After the user successfully submits
+     * the form, the room may queue the request for review by the room admins or may immediately
+     * add the user to the member list by changing the user's affiliation from "none" to "member.<p>
+     *
+     * If the desired room nickname is already reserved for that room, the room will return a
+     * "Conflict" error to the user (error code 409). If the room does not support registration,
+     * it will return a "Service Unavailable" error to the user (error code 503).
+     *
+     * @param form the completed registration form.
+     * @throws XMPPException if an error occurs submitting the registration form. In particular, a
+     *      409 error can occur if the desired room nickname is already reserved for that room;
+     *      or a 503 error can occur if the room does not support registration.
+     */
+    public void sendRegistrationForm(Form form) throws XMPPException {
+        Registration reg = new Registration();
+        reg.setType(IQ.Type.SET);
+        reg.setTo(room);
+        reg.addExtension(form.getDataFormToSend());
+
+        PacketFilter filter =
+            new AndFilter(new PacketIDFilter(reg.getPacketID()), new PacketTypeFilter(IQ.class));
+        PacketCollector collector = connection.createPacketCollector(filter);
+        connection.sendPacket(reg);
+        IQ result = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        collector.cancel();
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getType() == IQ.Type.ERROR) {
+            throw new XMPPException(result.getError());
+        }
+    }
+
+    /**
+     * Sends a request to the server to destroy the room. The sender of the request
+     * should be the room's owner. If the sender of the destroy request is not the room's owner
+     * then the server will answer a "Forbidden" error (403).
+     *
+     * @param reason the reason for the room destruction.
+     * @param alternateJID the JID of an alternate location.
+     * @throws XMPPException if an error occurs while trying to destroy the room.
+     *      An error can occur which will be wrapped by an XMPPException --
+     *      XMPP error code 403. The error code can be used to present more
+     *      appropiate error messages to end-users.
+     */
+    public void destroy(String reason, String alternateJID) throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+
+        // Create the reason for the room destruction
+        MUCOwner.Destroy destroy = new MUCOwner.Destroy();
+        destroy.setReason(reason);
+        destroy.setJid(alternateJID);
+        iq.setDestroy(destroy);
+
+        // Wait for a presence packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the room destruction request.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+        // Reset occupant information.
+        occupantsMap.clear();
+        nickname = null;
+        joined = false;
+        userHasLeft();
+    }
+
+    /**
+     * Invites another user to the room in which one is an occupant. The invitation
+     * will be sent to the room which in turn will forward the invitation to the invitee.<p>
+     *
+     * If the room is password-protected, the invitee will receive a password to use to join
+     * the room. If the room is members-only, the the invitee may be added to the member list.
+     *
+     * @param user the user to invite to the room.(e.g. hecate@shakespeare.lit)
+     * @param reason the reason why the user is being invited.
+     */
+    public void invite(String user, String reason) {
+        invite(new Message(), user, reason);
+    }
+
+    /**
+     * Invites another user to the room in which one is an occupant using a given Message. The invitation
+     * will be sent to the room which in turn will forward the invitation to the invitee.<p>
+     *
+     * If the room is password-protected, the invitee will receive a password to use to join
+     * the room. If the room is members-only, the the invitee may be added to the member list.
+     *
+     * @param message the message to use for sending the invitation.
+     * @param user the user to invite to the room.(e.g. hecate@shakespeare.lit)
+     * @param reason the reason why the user is being invited.
+     */
+    public void invite(Message message, String user, String reason) {
+        // TODO listen for 404 error code when inviter supplies a non-existent JID
+        message.setTo(room);
+
+        // Create the MUCUser packet that will include the invitation
+        MUCUser mucUser = new MUCUser();
+        MUCUser.Invite invite = new MUCUser.Invite();
+        invite.setTo(user);
+        invite.setReason(reason);
+        mucUser.setInvite(invite);
+        // Add the MUCUser packet that includes the invitation to the message
+        message.addExtension(mucUser);
+
+        connection.sendPacket(message);
+    }
+
+    /**
+     * Informs the sender of an invitation that the invitee declines the invitation. The rejection
+     * will be sent to the room which in turn will forward the rejection to the inviter.
+     *
+     * @param conn the connection to use for sending the rejection.
+     * @param room the room that sent the original invitation.
+     * @param inviter the inviter of the declined invitation.
+     * @param reason the reason why the invitee is declining the invitation.
+     */
+    public static void decline(Connection conn, String room, String inviter, String reason) {
+        Message message = new Message(room);
+
+        // Create the MUCUser packet that will include the rejection
+        MUCUser mucUser = new MUCUser();
+        MUCUser.Decline decline = new MUCUser.Decline();
+        decline.setTo(inviter);
+        decline.setReason(reason);
+        mucUser.setDecline(decline);
+        // Add the MUCUser packet that includes the rejection
+        message.addExtension(mucUser);
+
+        conn.sendPacket(message);
+    }
+
+    /**
+     * Adds a listener to invitation notifications. The listener will be fired anytime
+     * an invitation is received.
+     *
+     * @param conn the connection where the listener will be applied.
+     * @param listener an invitation listener.
+     */
+    public static void addInvitationListener(Connection conn, InvitationListener listener) {
+        InvitationsMonitor.getInvitationsMonitor(conn).addInvitationListener(listener);
+    }
+
+    /**
+     * Removes a listener to invitation notifications. The listener will be fired anytime
+     * an invitation is received.
+     *
+     * @param conn the connection where the listener was applied.
+     * @param listener an invitation listener.
+     */
+    public static void removeInvitationListener(Connection conn, InvitationListener listener) {
+        InvitationsMonitor.getInvitationsMonitor(conn).removeInvitationListener(listener);
+    }
+
+    /**
+     * Adds a listener to invitation rejections notifications. The listener will be fired anytime
+     * an invitation is declined.
+     *
+     * @param listener an invitation rejection listener.
+     */
+    public void addInvitationRejectionListener(InvitationRejectionListener listener) {
+        synchronized (invitationRejectionListeners) {
+            if (!invitationRejectionListeners.contains(listener)) {
+                invitationRejectionListeners.add(listener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener from invitation rejections notifications. The listener will be fired
+     * anytime an invitation is declined.
+     *
+     * @param listener an invitation rejection listener.
+     */
+    public void removeInvitationRejectionListener(InvitationRejectionListener listener) {
+        synchronized (invitationRejectionListeners) {
+            invitationRejectionListeners.remove(listener);
+        }
+    }
+
+    /**
+     * Fires invitation rejection listeners.
+     *
+     * @param invitee the user being invited.
+     * @param reason the reason for the rejection
+     */
+    private void fireInvitationRejectionListeners(String invitee, String reason) {
+        InvitationRejectionListener[] listeners;
+        synchronized (invitationRejectionListeners) {
+            listeners = new InvitationRejectionListener[invitationRejectionListeners.size()];
+            invitationRejectionListeners.toArray(listeners);
+        }
+        for (InvitationRejectionListener listener : listeners) {
+            listener.invitationDeclined(invitee, reason);
+        }
+    }
+
+    /**
+     * Adds a listener to subject change notifications. The listener will be fired anytime
+     * the room's subject changes.
+     *
+     * @param listener a subject updated listener.
+     */
+    public void addSubjectUpdatedListener(SubjectUpdatedListener listener) {
+        synchronized (subjectUpdatedListeners) {
+            if (!subjectUpdatedListeners.contains(listener)) {
+                subjectUpdatedListeners.add(listener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener from subject change notifications. The listener will be fired
+     * anytime the room's subject changes.
+     *
+     * @param listener a subject updated listener.
+     */
+    public void removeSubjectUpdatedListener(SubjectUpdatedListener listener) {
+        synchronized (subjectUpdatedListeners) {
+            subjectUpdatedListeners.remove(listener);
+        }
+    }
+
+    /**
+     * Fires subject updated listeners.
+     */
+    private void fireSubjectUpdatedListeners(String subject, String from) {
+        SubjectUpdatedListener[] listeners;
+        synchronized (subjectUpdatedListeners) {
+            listeners = new SubjectUpdatedListener[subjectUpdatedListeners.size()];
+            subjectUpdatedListeners.toArray(listeners);
+        }
+        for (SubjectUpdatedListener listener : listeners) {
+            listener.subjectUpdated(subject, from);
+        }
+    }
+
+    /**
+     * Adds a new {@link PacketInterceptor} that will be invoked every time a new presence
+     * is going to be sent by this MultiUserChat to the server. Packet interceptors may
+     * add new extensions to the presence that is going to be sent to the MUC service.
+     *
+     * @param presenceInterceptor the new packet interceptor that will intercept presence packets.
+     */
+    public void addPresenceInterceptor(PacketInterceptor presenceInterceptor) {
+        presenceInterceptors.add(presenceInterceptor);
+    }
+
+    /**
+     * Removes a {@link PacketInterceptor} that was being invoked every time a new presence
+     * was being sent by this MultiUserChat to the server. Packet interceptors may
+     * add new extensions to the presence that is going to be sent to the MUC service.
+     *
+     * @param presenceInterceptor the packet interceptor to remove.
+     */
+    public void removePresenceInterceptor(PacketInterceptor presenceInterceptor) {
+        presenceInterceptors.remove(presenceInterceptor);
+    }
+
+    /**
+     * Returns the last known room's subject or <tt>null</tt> if the user hasn't joined the room
+     * or the room does not have a subject yet. In case the room has a subject, as soon as the
+     * user joins the room a message with the current room's subject will be received.<p>
+     *
+     * To be notified every time the room's subject change you should add a listener
+     * to this room. {@link #addSubjectUpdatedListener(SubjectUpdatedListener)}<p>
+     *
+     * To change the room's subject use {@link #changeSubject(String)}.
+     *
+     * @return the room's subject or <tt>null</tt> if the user hasn't joined the room or the
+     * room does not have a subject yet.
+     */
+    public String getSubject() {
+        return subject;
+    }
+
+    /**
+     * Returns the reserved room nickname for the user in the room. A user may have a reserved
+     * nickname, for example through explicit room registration or database integration. In such
+     * cases it may be desirable for the user to discover the reserved nickname before attempting
+     * to enter the room.
+     *
+     * @return the reserved room nickname or <tt>null</tt> if none.
+     */
+    public String getReservedNickname() {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(
+                    room,
+                    "x-roomuser-item");
+            // Look for an Identity that holds the reserved nickname and return its name
+            for (Iterator<DiscoverInfo.Identity> identities = result.getIdentities();
+                 identities.hasNext();) {
+                DiscoverInfo.Identity identity = identities.next();
+                return identity.getName();
+            }
+            // If no Identity was found then the user does not have a reserved room nickname
+            return null;
+        }
+        catch (XMPPException e) {
+            e.printStackTrace();
+            return null;
+        }
+    }
+
+    /**
+     * Returns the nickname that was used to join the room, or <tt>null</tt> if not
+     * currently joined.
+     *
+     * @return the nickname currently being used.
+     */
+    public String getNickname() {
+        return nickname;
+    }
+
+    /**
+     * Changes the occupant's nickname to a new nickname within the room. Each room occupant
+     * will receive two presence packets. One of type "unavailable" for the old nickname and one
+     * indicating availability for the new nickname. The unavailable presence will contain the new
+     * nickname and an appropriate status code (namely 303) as extended presence information. The
+     * status code 303 indicates that the occupant is changing his/her nickname.
+     *
+     * @param nickname the new nickname within the room.
+     * @throws XMPPException if the new nickname is already in use by another occupant.
+     */
+    public void changeNickname(String nickname) throws XMPPException {
+        if (nickname == null || nickname.equals("")) {
+            throw new IllegalArgumentException("Nickname must not be null or blank.");
+        }
+        // Check that we already have joined the room before attempting to change the
+        // nickname.
+        if (!joined) {
+            throw new IllegalStateException("Must be logged into the room to change nickname.");
+        }
+        // We change the nickname by sending a presence packet where the "to"
+        // field is in the form "roomName@service/nickname"
+        // We don't have to signal the MUC support again
+        Presence joinPresence = new Presence(Presence.Type.available);
+        joinPresence.setTo(room + "/" + nickname);
+        // Invoke presence interceptors so that extra information can be dynamically added
+        for (PacketInterceptor packetInterceptor : presenceInterceptors) {
+            packetInterceptor.interceptPacket(joinPresence);
+        }
+
+        // Wait for a presence packet back from the server.
+        PacketFilter responseFilter =
+            new AndFilter(
+                new FromMatchesFilter(room + "/" + nickname),
+                new PacketTypeFilter(Presence.class));
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send join packet.
+        connection.sendPacket(joinPresence);
+        // Wait up to a certain number of seconds for a reply.
+        Presence presence =
+            (Presence) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (presence == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (presence.getError() != null) {
+            throw new XMPPException(presence.getError());
+        }
+        this.nickname = nickname;
+    }
+
+    /**
+     * Changes the occupant's availability status within the room. The presence type
+     * will remain available but with a new status that describes the presence update and
+     * a new presence mode (e.g. Extended away).
+     *
+     * @param status a text message describing the presence update.
+     * @param mode the mode type for the presence update.
+     */
+    public void changeAvailabilityStatus(String status, Presence.Mode mode) {
+        if (nickname == null || nickname.equals("")) {
+            throw new IllegalArgumentException("Nickname must not be null or blank.");
+        }
+        // Check that we already have joined the room before attempting to change the
+        // availability status.
+        if (!joined) {
+            throw new IllegalStateException(
+                "Must be logged into the room to change the " + "availability status.");
+        }
+        // We change the availability status by sending a presence packet to the room with the
+        // new presence status and mode
+        Presence joinPresence = new Presence(Presence.Type.available);
+        joinPresence.setStatus(status);
+        joinPresence.setMode(mode);
+        joinPresence.setTo(room + "/" + nickname);
+        // Invoke presence interceptors so that extra information can be dynamically added
+        for (PacketInterceptor packetInterceptor : presenceInterceptors) {
+            packetInterceptor.interceptPacket(joinPresence);
+        }
+
+        // Send join packet.
+        connection.sendPacket(joinPresence);
+    }
+
+    /**
+     * Kicks a visitor or participant from the room. The kicked occupant will receive a presence
+     * of type "unavailable" including a status code 307 and optionally along with the reason
+     * (if provided) and the bare JID of the user who initiated the kick. After the occupant
+     * was kicked from the room, the rest of the occupants will receive a presence of type
+     * "unavailable". The presence will include a status code 307 which means that the occupant
+     * was kicked from the room.
+     *
+     * @param nickname the nickname of the participant or visitor to kick from the room
+     * (e.g. "john").
+     * @param reason the reason why the participant or visitor is being kicked from the room.
+     * @throws XMPPException if an error occurs kicking the occupant. In particular, a
+     *      405 error can occur if a moderator or a user with an affiliation of "owner" or "admin"
+     *      was intended to be kicked (i.e. Not Allowed error); or a
+     *      403 error can occur if the occupant that intended to kick another occupant does
+     *      not have kicking privileges (i.e. Forbidden error); or a
+     *      400 error can occur if the provided nickname is not present in the room.
+     */
+    public void kickParticipant(String nickname, String reason) throws XMPPException {
+        changeRole(nickname, "none", reason);
+    }
+
+    /**
+     * Grants voice to visitors in the room. In a moderated room, a moderator may want to manage
+     * who does and does not have "voice" in the room. To have voice means that a room occupant
+     * is able to send messages to the room occupants.
+     *
+     * @param nicknames the nicknames of the visitors to grant voice in the room (e.g. "john").
+     * @throws XMPPException if an error occurs granting voice to a visitor. In particular, a
+     *      403 error can occur if the occupant that intended to grant voice is not
+     *      a moderator in this room (i.e. Forbidden error); or a
+     *      400 error can occur if the provided nickname is not present in the room.
+     */
+    public void grantVoice(Collection<String> nicknames) throws XMPPException {
+        changeRole(nicknames, "participant");
+    }
+
+    /**
+     * Grants voice to a visitor in the room. In a moderated room, a moderator may want to manage
+     * who does and does not have "voice" in the room. To have voice means that a room occupant
+     * is able to send messages to the room occupants.
+     *
+     * @param nickname the nickname of the visitor to grant voice in the room (e.g. "john").
+     * @throws XMPPException if an error occurs granting voice to a visitor. In particular, a
+     *      403 error can occur if the occupant that intended to grant voice is not
+     *      a moderator in this room (i.e. Forbidden error); or a
+     *      400 error can occur if the provided nickname is not present in the room.
+     */
+    public void grantVoice(String nickname) throws XMPPException {
+        changeRole(nickname, "participant", null);
+    }
+
+    /**
+     * Revokes voice from participants in the room. In a moderated room, a moderator may want to
+     * revoke an occupant's privileges to speak. To have voice means that a room occupant
+     * is able to send messages to the room occupants.
+     *
+     * @param nicknames the nicknames of the participants to revoke voice (e.g. "john").
+     * @throws XMPPException if an error occurs revoking voice from a participant. In particular, a
+     *      405 error can occur if a moderator or a user with an affiliation of "owner" or "admin"
+     *      was tried to revoke his voice (i.e. Not Allowed error); or a
+     *      400 error can occur if the provided nickname is not present in the room.
+     */
+    public void revokeVoice(Collection<String> nicknames) throws XMPPException {
+        changeRole(nicknames, "visitor");
+    }
+
+    /**
+     * Revokes voice from a participant in the room. In a moderated room, a moderator may want to
+     * revoke an occupant's privileges to speak. To have voice means that a room occupant
+     * is able to send messages to the room occupants.
+     *
+     * @param nickname the nickname of the participant to revoke voice (e.g. "john").
+     * @throws XMPPException if an error occurs revoking voice from a participant. In particular, a
+     *      405 error can occur if a moderator or a user with an affiliation of "owner" or "admin"
+     *      was tried to revoke his voice (i.e. Not Allowed error); or a
+     *      400 error can occur if the provided nickname is not present in the room.
+     */
+    public void revokeVoice(String nickname) throws XMPPException {
+        changeRole(nickname, "visitor", null);
+    }
+
+    /**
+     * Bans users from the room. An admin or owner of the room can ban users from a room. This
+     * means that the banned user will no longer be able to join the room unless the ban has been
+     * removed. If the banned user was present in the room then he/she will be removed from the
+     * room and notified that he/she was banned along with the reason (if provided) and the bare
+     * XMPP user ID of the user who initiated the ban.
+     *
+     * @param jids the bare XMPP user IDs of the users to ban.
+     * @throws XMPPException if an error occurs banning a user. In particular, a
+     *      405 error can occur if a moderator or a user with an affiliation of "owner" or "admin"
+     *      was tried to be banned (i.e. Not Allowed error).
+     */
+    public void banUsers(Collection<String> jids) throws XMPPException {
+        changeAffiliationByAdmin(jids, "outcast");
+    }
+
+    /**
+     * Bans a user from the room. An admin or owner of the room can ban users from a room. This
+     * means that the banned user will no longer be able to join the room unless the ban has been
+     * removed. If the banned user was present in the room then he/she will be removed from the
+     * room and notified that he/she was banned along with the reason (if provided) and the bare
+     * XMPP user ID of the user who initiated the ban.
+     *
+     * @param jid the bare XMPP user ID of the user to ban (e.g. "user@host.org").
+     * @param reason the optional reason why the user was banned.
+     * @throws XMPPException if an error occurs banning a user. In particular, a
+     *      405 error can occur if a moderator or a user with an affiliation of "owner" or "admin"
+     *      was tried to be banned (i.e. Not Allowed error).
+     */
+    public void banUser(String jid, String reason) throws XMPPException {
+        changeAffiliationByAdmin(jid, "outcast", reason);
+    }
+
+    /**
+     * Grants membership to other users. Only administrators are able to grant membership. A user
+     * that becomes a room member will be able to enter a room of type Members-Only (i.e. a room
+     * that a user cannot enter without being on the member list).
+     *
+     * @param jids the XMPP user IDs of the users to grant membership.
+     * @throws XMPPException if an error occurs granting membership to a user.
+     */
+    public void grantMembership(Collection<String> jids) throws XMPPException {
+        changeAffiliationByAdmin(jids, "member");
+    }
+
+    /**
+     * Grants membership to a user. Only administrators are able to grant membership. A user
+     * that becomes a room member will be able to enter a room of type Members-Only (i.e. a room
+     * that a user cannot enter without being on the member list).
+     *
+     * @param jid the XMPP user ID of the user to grant membership (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs granting membership to a user.
+     */
+    public void grantMembership(String jid) throws XMPPException {
+        changeAffiliationByAdmin(jid, "member", null);
+    }
+
+    /**
+     * Revokes users' membership. Only administrators are able to revoke membership. A user
+     * that becomes a room member will be able to enter a room of type Members-Only (i.e. a room
+     * that a user cannot enter without being on the member list). If the user is in the room and
+     * the room is of type members-only then the user will be removed from the room.
+     *
+     * @param jids the bare XMPP user IDs of the users to revoke membership.
+     * @throws XMPPException if an error occurs revoking membership to a user.
+     */
+    public void revokeMembership(Collection<String> jids) throws XMPPException {
+        changeAffiliationByAdmin(jids, "none");
+    }
+
+    /**
+     * Revokes a user's membership. Only administrators are able to revoke membership. A user
+     * that becomes a room member will be able to enter a room of type Members-Only (i.e. a room
+     * that a user cannot enter without being on the member list). If the user is in the room and
+     * the room is of type members-only then the user will be removed from the room.
+     *
+     * @param jid the bare XMPP user ID of the user to revoke membership (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs revoking membership to a user.
+     */
+    public void revokeMembership(String jid) throws XMPPException {
+        changeAffiliationByAdmin(jid, "none", null);
+    }
+
+    /**
+     * Grants moderator privileges to participants or visitors. Room administrators may grant
+     * moderator privileges. A moderator is allowed to kick users, grant and revoke voice, invite
+     * other users, modify room's subject plus all the partcipants privileges.
+     *
+     * @param nicknames the nicknames of the occupants to grant moderator privileges.
+     * @throws XMPPException if an error occurs granting moderator privileges to a user.
+     */
+    public void grantModerator(Collection<String> nicknames) throws XMPPException {
+        changeRole(nicknames, "moderator");
+    }
+
+    /**
+     * Grants moderator privileges to a participant or visitor. Room administrators may grant
+     * moderator privileges. A moderator is allowed to kick users, grant and revoke voice, invite
+     * other users, modify room's subject plus all the partcipants privileges.
+     *
+     * @param nickname the nickname of the occupant to grant moderator privileges.
+     * @throws XMPPException if an error occurs granting moderator privileges to a user.
+     */
+    public void grantModerator(String nickname) throws XMPPException {
+        changeRole(nickname, "moderator", null);
+    }
+
+    /**
+     * Revokes moderator privileges from other users. The occupant that loses moderator
+     * privileges will become a participant. Room administrators may revoke moderator privileges
+     * only to occupants whose affiliation is member or none. This means that an administrator is
+     * not allowed to revoke moderator privileges from other room administrators or owners.
+     *
+     * @param nicknames the nicknames of the occupants to revoke moderator privileges.
+     * @throws XMPPException if an error occurs revoking moderator privileges from a user.
+     */
+    public void revokeModerator(Collection<String> nicknames) throws XMPPException {
+        changeRole(nicknames, "participant");
+    }
+
+    /**
+     * Revokes moderator privileges from another user. The occupant that loses moderator
+     * privileges will become a participant. Room administrators may revoke moderator privileges
+     * only to occupants whose affiliation is member or none. This means that an administrator is
+     * not allowed to revoke moderator privileges from other room administrators or owners.
+     *
+     * @param nickname the nickname of the occupant to revoke moderator privileges.
+     * @throws XMPPException if an error occurs revoking moderator privileges from a user.
+     */
+    public void revokeModerator(String nickname) throws XMPPException {
+        changeRole(nickname, "participant", null);
+    }
+
+    /**
+     * Grants ownership privileges to other users. Room owners may grant ownership privileges.
+     * Some room implementations will not allow to grant ownership privileges to other users.
+     * An owner is allowed to change defining room features as well as perform all administrative
+     * functions.
+     *
+     * @param jids the collection of bare XMPP user IDs of the users to grant ownership.
+     * @throws XMPPException if an error occurs granting ownership privileges to a user.
+     */
+    public void grantOwnership(Collection<String> jids) throws XMPPException {
+        changeAffiliationByAdmin(jids, "owner");
+    }
+
+    /**
+     * Grants ownership privileges to another user. Room owners may grant ownership privileges.
+     * Some room implementations will not allow to grant ownership privileges to other users.
+     * An owner is allowed to change defining room features as well as perform all administrative
+     * functions.
+     *
+     * @param jid the bare XMPP user ID of the user to grant ownership (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs granting ownership privileges to a user.
+     */
+    public void grantOwnership(String jid) throws XMPPException {
+        changeAffiliationByAdmin(jid, "owner", null);
+    }
+
+    /**
+     * Revokes ownership privileges from other users. The occupant that loses ownership
+     * privileges will become an administrator. Room owners may revoke ownership privileges.
+     * Some room implementations will not allow to grant ownership privileges to other users.
+     *
+     * @param jids the bare XMPP user IDs of the users to revoke ownership.
+     * @throws XMPPException if an error occurs revoking ownership privileges from a user.
+     */
+    public void revokeOwnership(Collection<String> jids) throws XMPPException {
+        changeAffiliationByAdmin(jids, "admin");
+    }
+
+    /**
+     * Revokes ownership privileges from another user. The occupant that loses ownership
+     * privileges will become an administrator. Room owners may revoke ownership privileges.
+     * Some room implementations will not allow to grant ownership privileges to other users.
+     *
+     * @param jid the bare XMPP user ID of the user to revoke ownership (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs revoking ownership privileges from a user.
+     */
+    public void revokeOwnership(String jid) throws XMPPException {
+        changeAffiliationByAdmin(jid, "admin", null);
+    }
+
+    /**
+     * Grants administrator privileges to other users. Room owners may grant administrator
+     * privileges to a member or unaffiliated user. An administrator is allowed to perform
+     * administrative functions such as banning users and edit moderator list.
+     *
+     * @param jids the bare XMPP user IDs of the users to grant administrator privileges.
+     * @throws XMPPException if an error occurs granting administrator privileges to a user.
+     */
+    public void grantAdmin(Collection<String> jids) throws XMPPException {
+        changeAffiliationByOwner(jids, "admin");
+    }
+
+    /**
+     * Grants administrator privileges to another user. Room owners may grant administrator
+     * privileges to a member or unaffiliated user. An administrator is allowed to perform
+     * administrative functions such as banning users and edit moderator list.
+     *
+     * @param jid the bare XMPP user ID of the user to grant administrator privileges
+     * (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs granting administrator privileges to a user.
+     */
+    public void grantAdmin(String jid) throws XMPPException {
+        changeAffiliationByOwner(jid, "admin");
+    }
+
+    /**
+     * Revokes administrator privileges from users. The occupant that loses administrator
+     * privileges will become a member. Room owners may revoke administrator privileges from
+     * a member or unaffiliated user.
+     *
+     * @param jids the bare XMPP user IDs of the user to revoke administrator privileges.
+     * @throws XMPPException if an error occurs revoking administrator privileges from a user.
+     */
+    public void revokeAdmin(Collection<String> jids) throws XMPPException {
+        changeAffiliationByOwner(jids, "member");
+    }
+
+    /**
+     * Revokes administrator privileges from a user. The occupant that loses administrator
+     * privileges will become a member. Room owners may revoke administrator privileges from
+     * a member or unaffiliated user.
+     *
+     * @param jid the bare XMPP user ID of the user to revoke administrator privileges
+     * (e.g. "user@host.org").
+     * @throws XMPPException if an error occurs revoking administrator privileges from a user.
+     */
+    public void revokeAdmin(String jid) throws XMPPException {
+        changeAffiliationByOwner(jid, "member");
+    }
+
+    private void changeAffiliationByOwner(String jid, String affiliation) throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        // Set the new affiliation.
+        MUCOwner.Item item = new MUCOwner.Item(affiliation);
+        item.setJid(jid);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    private void changeAffiliationByOwner(Collection<String> jids, String affiliation)
+            throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        for (String jid : jids) {
+            // Set the new affiliation.
+            MUCOwner.Item item = new MUCOwner.Item(affiliation);
+            item.setJid(jid);
+            iq.addItem(item);
+        }
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    /**
+     * Tries to change the affiliation with an 'muc#admin' namespace
+     *
+     * @param jid
+     * @param affiliation
+     * @param reason the reason for the affiliation change (optional)
+     * @throws XMPPException
+     */
+    private void changeAffiliationByAdmin(String jid, String affiliation, String reason)
+            throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        // Set the new affiliation.
+        MUCAdmin.Item item = new MUCAdmin.Item(affiliation, null);
+        item.setJid(jid);
+        if(reason != null)
+            item.setReason(reason);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    private void changeAffiliationByAdmin(Collection<String> jids, String affiliation)
+            throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        for (String jid : jids) {
+            // Set the new affiliation.
+            MUCAdmin.Item item = new MUCAdmin.Item(affiliation, null);
+            item.setJid(jid);
+            iq.addItem(item);
+        }
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    private void changeRole(String nickname, String role, String reason) throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        // Set the new role.
+        MUCAdmin.Item item = new MUCAdmin.Item(null, role);
+        item.setNick(nickname);
+        item.setReason(reason);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    private void changeRole(Collection<String> nicknames, String role) throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.SET);
+        for (String nickname : nicknames) {
+            // Set the new role.
+            MUCAdmin.Item item = new MUCAdmin.Item(null, role);
+            item.setNick(nickname);
+            iq.addItem(item);
+        }
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the change request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        IQ answer = (IQ) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    /**
+     * Returns the number of occupants in the group chat.<p>
+     *
+     * Note: this value will only be accurate after joining the group chat, and
+     * may fluctuate over time. If you query this value directly after joining the
+     * group chat it may not be accurate, as it takes a certain amount of time for
+     * the server to send all presence packets to this client.
+     *
+     * @return the number of occupants in the group chat.
+     */
+    public int getOccupantsCount() {
+        return occupantsMap.size();
+    }
+
+    /**
+     * Returns an Iterator (of Strings) for the list of fully qualified occupants
+     * in the group chat. For example, "conference@chat.jivesoftware.com/SomeUser".
+     * Typically, a client would only display the nickname of the occupant. To
+     * get the nickname from the fully qualified name, use the
+     * {@link org.jivesoftware.smack.util.StringUtils#parseResource(String)} method.
+     * Note: this value will only be accurate after joining the group chat, and may
+     * fluctuate over time.
+     *
+     * @return an Iterator for the occupants in the group chat.
+     */
+    public Iterator<String> getOccupants() {
+        return Collections.unmodifiableList(new ArrayList<String>(occupantsMap.keySet()))
+                .iterator();
+    }
+
+    /**
+     * Returns the presence info for a particular user, or <tt>null</tt> if the user
+     * is not in the room.<p>
+     *
+     * @param user the room occupant to search for his presence. The format of user must
+     * be: roomName@service/nickname (e.g. darkcave@macbeth.shakespeare.lit/thirdwitch).
+     * @return the occupant's current presence, or <tt>null</tt> if the user is unavailable
+     *      or if no presence information is available.
+     */
+    public Presence getOccupantPresence(String user) {
+        return occupantsMap.get(user);
+    }
+
+    /**
+     * Returns the Occupant information for a particular occupant, or <tt>null</tt> if the
+     * user is not in the room. The Occupant object may include information such as full
+     * JID of the user as well as the role and affiliation of the user in the room.<p>
+     *
+     * @param user the room occupant to search for his presence. The format of user must
+     * be: roomName@service/nickname (e.g. darkcave@macbeth.shakespeare.lit/thirdwitch).
+     * @return the Occupant or <tt>null</tt> if the user is unavailable (i.e. not in the room).
+     */
+    public Occupant getOccupant(String user) {
+        Presence presence = occupantsMap.get(user);
+        if (presence != null) {
+            return new Occupant(presence);
+        }
+        return null;
+    }
+
+    /**
+     * Adds a packet listener that will be notified of any new Presence packets
+     * sent to the group chat. Using a listener is a suitable way to know when the list
+     * of occupants should be re-loaded due to any changes.
+     *
+     * @param listener a packet listener that will be notified of any presence packets
+     *      sent to the group chat.
+     */
+    public void addParticipantListener(PacketListener listener) {
+        connection.addPacketListener(listener, presenceFilter);
+        connectionListeners.add(listener);
+    }
+
+    /**
+     * Remoces a packet listener that was being notified of any new Presence packets
+     * sent to the group chat.
+     *
+     * @param listener a packet listener that was being notified of any presence packets
+     *      sent to the group chat.
+     */
+    public void removeParticipantListener(PacketListener listener) {
+        connection.removePacketListener(listener);
+        connectionListeners.remove(listener);
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> with the room owners.
+     *
+     * @return a collection of <code>Affiliate</code> with the room owners.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Affiliate> getOwners() throws XMPPException {
+        return getAffiliatesByAdmin("owner");
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> with the room administrators.
+     *
+     * @return a collection of <code>Affiliate</code> with the room administrators.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Affiliate> getAdmins() throws XMPPException {
+        return getAffiliatesByOwner("admin");
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> with the room members.
+     *
+     * @return a collection of <code>Affiliate</code> with the room members.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Affiliate> getMembers() throws XMPPException {
+        return getAffiliatesByAdmin("member");
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> with the room outcasts.
+     *
+     * @return a collection of <code>Affiliate</code> with the room outcasts.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Affiliate> getOutcasts() throws XMPPException {
+        return getAffiliatesByAdmin("outcast");
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> that have the specified room affiliation
+     * sending a request in the owner namespace.
+     *
+     * @param affiliation the affiliation of the users in the room.
+     * @return a collection of <code>Affiliate</code> that have the specified room affiliation.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    private Collection<Affiliate> getAffiliatesByOwner(String affiliation) throws XMPPException {
+        MUCOwner iq = new MUCOwner();
+        iq.setTo(room);
+        iq.setType(IQ.Type.GET);
+        // Set the specified affiliation. This may request the list of owners/admins/members/outcasts.
+        MUCOwner.Item item = new MUCOwner.Item(affiliation);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        MUCOwner answer = (MUCOwner) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+        // Get the list of affiliates from the server's answer
+        List<Affiliate> affiliates = new ArrayList<Affiliate>();
+        for (Iterator<MUCOwner.Item> it = answer.getItems(); it.hasNext();) {
+            affiliates.add(new Affiliate(it.next()));
+        }
+        return affiliates;
+    }
+
+    /**
+     * Returns a collection of <code>Affiliate</code> that have the specified room affiliation
+     * sending a request in the admin namespace.
+     *
+     * @param affiliation the affiliation of the users in the room.
+     * @return a collection of <code>Affiliate</code> that have the specified room affiliation.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    private Collection<Affiliate> getAffiliatesByAdmin(String affiliation) throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.GET);
+        // Set the specified affiliation. This may request the list of owners/admins/members/outcasts.
+        MUCAdmin.Item item = new MUCAdmin.Item(affiliation, null);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        MUCAdmin answer = (MUCAdmin) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+        // Get the list of affiliates from the server's answer
+        List<Affiliate> affiliates = new ArrayList<Affiliate>();
+        for (Iterator<MUCAdmin.Item> it = answer.getItems(); it.hasNext();) {
+            affiliates.add(new Affiliate(it.next()));
+        }
+        return affiliates;
+    }
+
+    /**
+     * Returns a collection of <code>Occupant</code> with the room moderators.
+     *
+     * @return a collection of <code>Occupant</code> with the room moderators.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Occupant> getModerators() throws XMPPException {
+        return getOccupants("moderator");
+    }
+
+    /**
+     * Returns a collection of <code>Occupant</code> with the room participants.
+     *
+     * @return a collection of <code>Occupant</code> with the room participants.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    public Collection<Occupant> getParticipants() throws XMPPException {
+        return getOccupants("participant");
+    }
+
+    /**
+     * Returns a collection of <code>Occupant</code> that have the specified room role.
+     *
+     * @param role the role of the occupant in the room.
+     * @return a collection of <code>Occupant</code> that have the specified room role.
+     * @throws XMPPException if an error occured while performing the request to the server or you
+     *         don't have enough privileges to get this information.
+     */
+    private Collection<Occupant> getOccupants(String role) throws XMPPException {
+        MUCAdmin iq = new MUCAdmin();
+        iq.setTo(room);
+        iq.setType(IQ.Type.GET);
+        // Set the specified role. This may request the list of moderators/participants.
+        MUCAdmin.Item item = new MUCAdmin.Item(null, role);
+        iq.addItem(item);
+
+        // Wait for a response packet back from the server.
+        PacketFilter responseFilter = new PacketIDFilter(iq.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send the request to the server.
+        connection.sendPacket(iq);
+        // Wait up to a certain number of seconds for a reply.
+        MUCAdmin answer = (MUCAdmin) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+        // Get the list of participants from the server's answer
+        List<Occupant> participants = new ArrayList<Occupant>();
+        for (Iterator<MUCAdmin.Item> it = answer.getItems(); it.hasNext();) {
+            participants.add(new Occupant(it.next()));
+        }
+        return participants;
+    }
+
+    /**
+     * Sends a message to the chat room.
+     *
+     * @param text the text of the message to send.
+     * @throws XMPPException if sending the message fails.
+     */
+    public void sendMessage(String text) throws XMPPException {
+        Message message = new Message(room, Message.Type.groupchat);
+        message.setBody(text);
+        connection.sendPacket(message);
+    }
+
+    /**
+     * Returns a new Chat for sending private messages to a given room occupant.
+     * The Chat's occupant address is the room's JID (i.e. roomName@service/nick). The server
+     * service will change the 'from' address to the sender's room JID and delivering the message
+     * to the intended recipient's full JID.
+     *
+     * @param occupant occupant unique room JID (e.g. 'darkcave@macbeth.shakespeare.lit/Paul').
+     * @param listener the listener is a message listener that will handle messages for the newly
+     * created chat.
+     * @return new Chat for sending private messages to a given room occupant.
+     */
+    public Chat createPrivateChat(String occupant, MessageListener listener) {
+        return connection.getChatManager().createChat(occupant, listener);
+    }
+
+    /**
+     * Creates a new Message to send to the chat room.
+     *
+     * @return a new Message addressed to the chat room.
+     */
+    public Message createMessage() {
+        return new Message(room, Message.Type.groupchat);
+    }
+
+    /**
+     * Sends a Message to the chat room.
+     *
+     * @param message the message.
+     * @throws XMPPException if sending the message fails.
+     */
+    public void sendMessage(Message message) throws XMPPException {
+        connection.sendPacket(message);
+    }
+
+    /**
+    * Polls for and returns the next message, or <tt>null</tt> if there isn't
+    * a message immediately available. This method provides significantly different
+    * functionalty than the {@link #nextMessage()} method since it's non-blocking.
+    * In other words, the method call will always return immediately, whereas the
+    * nextMessage method will return only when a message is available (or after
+    * a specific timeout).
+    *
+    * @return the next message if one is immediately available and
+    *      <tt>null</tt> otherwise.
+    */
+    public Message pollMessage() {
+        return (Message) messageCollector.pollResult();
+    }
+
+    /**
+     * Returns the next available message in the chat. The method call will block
+     * (not return) until a message is available.
+     *
+     * @return the next message.
+     */
+    public Message nextMessage() {
+        return (Message) messageCollector.nextResult();
+    }
+
+    /**
+     * Returns the next available message in the chat. The method call will block
+     * (not return) until a packet is available or the <tt>timeout</tt> has elapased.
+     * If the timeout elapses without a result, <tt>null</tt> will be returned.
+     *
+     * @param timeout the maximum amount of time to wait for the next message.
+     * @return the next message, or <tt>null</tt> if the timeout elapses without a
+     *      message becoming available.
+     */
+    public Message nextMessage(long timeout) {
+        return (Message) messageCollector.nextResult(timeout);
+    }
+
+    /**
+     * Adds a packet listener that will be notified of any new messages in the
+     * group chat. Only "group chat" messages addressed to this group chat will
+     * be delivered to the listener. If you wish to listen for other packets
+     * that may be associated with this group chat, you should register a
+     * PacketListener directly with the Connection with the appropriate
+     * PacketListener.
+     *
+     * @param listener a packet listener.
+     */
+    public void addMessageListener(PacketListener listener) {
+        connection.addPacketListener(listener, messageFilter);
+        connectionListeners.add(listener);
+    }
+
+    /**
+     * Removes a packet listener that was being notified of any new messages in the
+     * multi user chat. Only "group chat" messages addressed to this multi user chat were
+     * being delivered to the listener.
+     *
+     * @param listener a packet listener.
+     */
+    public void removeMessageListener(PacketListener listener) {
+        connection.removePacketListener(listener);
+        connectionListeners.remove(listener);
+    }
+
+    /**
+     * Changes the subject within the room. As a default, only users with a role of "moderator"
+     * are allowed to change the subject in a room. Although some rooms may be configured to
+     * allow a mere participant or even a visitor to change the subject.
+     *
+     * @param subject the new room's subject to set.
+     * @throws XMPPException if someone without appropriate privileges attempts to change the
+     *          room subject will throw an error with code 403 (i.e. Forbidden)
+     */
+    public void changeSubject(final String subject) throws XMPPException {
+        Message message = new Message(room, Message.Type.groupchat);
+        message.setSubject(subject);
+        // Wait for an error or confirmation message back from the server.
+        PacketFilter responseFilter =
+            new AndFilter(
+                new FromMatchesFilter(room),
+                new PacketTypeFilter(Message.class));
+        responseFilter = new AndFilter(responseFilter, new PacketFilter() {
+            public boolean accept(Packet packet) {
+                Message msg = (Message) packet;
+                return subject.equals(msg.getSubject());
+            }
+        });
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        // Send change subject packet.
+        connection.sendPacket(message);
+        // Wait up to a certain number of seconds for a reply.
+        Message answer =
+            (Message) response.nextResult(SmackConfiguration.getPacketReplyTimeout());
+        // Stop queuing results
+        response.cancel();
+
+        if (answer == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (answer.getError() != null) {
+            throw new XMPPException(answer.getError());
+        }
+    }
+
+    /**
+     * Notification message that the user has joined the room.
+     */
+    private synchronized void userHasJoined() {
+        // Update the list of joined rooms through this connection
+        List<String> rooms = joinedRooms.get(connection);
+        if (rooms == null) {
+            rooms = new ArrayList<String>();
+            joinedRooms.put(connection, rooms);
+        }
+        rooms.add(room);
+    }
+
+    /**
+     * Notification message that the user has left the room.
+     */
+    private synchronized void userHasLeft() {
+        // Update the list of joined rooms through this connection
+        List<String> rooms = joinedRooms.get(connection);
+        if (rooms == null) {
+            return;
+        }
+        rooms.remove(room);
+        cleanup();
+    }
+
+    /**
+     * Returns the MUCUser packet extension included in the packet or <tt>null</tt> if none.
+     *
+     * @param packet the packet that may include the MUCUser extension.
+     * @return the MUCUser found in the packet.
+     */
+    private MUCUser getMUCUserExtension(Packet packet) {
+        if (packet != null) {
+            // Get the MUC User extension
+            return (MUCUser) packet.getExtension("x", "http://jabber.org/protocol/muc#user");
+        }
+        return null;
+    }
+
+    /**
+     * Adds a listener that will be notified of changes in your status in the room
+     * such as the user being kicked, banned, or granted admin permissions.
+     *
+     * @param listener a user status listener.
+     */
+    public void addUserStatusListener(UserStatusListener listener) {
+        synchronized (userStatusListeners) {
+            if (!userStatusListeners.contains(listener)) {
+                userStatusListeners.add(listener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener that was being notified of changes in your status in the room
+     * such as the user being kicked, banned, or granted admin permissions.
+     *
+     * @param listener a user status listener.
+     */
+    public void removeUserStatusListener(UserStatusListener listener) {
+        synchronized (userStatusListeners) {
+            userStatusListeners.remove(listener);
+        }
+    }
+
+    private void fireUserStatusListeners(String methodName, Object[] params) {
+        UserStatusListener[] listeners;
+        synchronized (userStatusListeners) {
+            listeners = new UserStatusListener[userStatusListeners.size()];
+            userStatusListeners.toArray(listeners);
+        }
+        // Get the classes of the method parameters
+        Class<?>[] paramClasses = new Class[params.length];
+        for (int i = 0; i < params.length; i++) {
+            paramClasses[i] = params[i].getClass();
+        }
+        try {
+            // Get the method to execute based on the requested methodName and parameters classes
+            Method method = UserStatusListener.class.getDeclaredMethod(methodName, paramClasses);
+            for (UserStatusListener listener : listeners) {
+                method.invoke(listener, params);
+            }
+        } catch (NoSuchMethodException e) {
+            e.printStackTrace();
+        } catch (InvocationTargetException e) {
+            e.printStackTrace();
+        } catch (IllegalAccessException e) {
+            e.printStackTrace();
+        }
+    }
+
+    /**
+     * Adds a listener that will be notified of changes in occupants status in the room
+     * such as the user being kicked, banned, or granted admin permissions.
+     *
+     * @param listener a participant status listener.
+     */
+    public void addParticipantStatusListener(ParticipantStatusListener listener) {
+        synchronized (participantStatusListeners) {
+            if (!participantStatusListeners.contains(listener)) {
+                participantStatusListeners.add(listener);
+            }
+        }
+    }
+
+    /**
+     * Removes a listener that was being notified of changes in occupants status in the room
+     * such as the user being kicked, banned, or granted admin permissions.
+     *
+     * @param listener a participant status listener.
+     */
+    public void removeParticipantStatusListener(ParticipantStatusListener listener) {
+        synchronized (participantStatusListeners) {
+            participantStatusListeners.remove(listener);
+        }
+    }
+
+    private void fireParticipantStatusListeners(String methodName, List<String> params) {
+        ParticipantStatusListener[] listeners;
+        synchronized (participantStatusListeners) {
+            listeners = new ParticipantStatusListener[participantStatusListeners.size()];
+            participantStatusListeners.toArray(listeners);
+        }
+        try {
+            // Get the method to execute based on the requested methodName and parameter
+            Class<?>[] classes = new Class[params.size()];
+            for (int i=0;i<params.size(); i++) {
+                classes[i] = String.class;
+            }
+            Method method = ParticipantStatusListener.class.getDeclaredMethod(methodName, classes);
+            for (ParticipantStatusListener listener : listeners) {
+                method.invoke(listener, params.toArray());
+            }
+        } catch (NoSuchMethodException e) {
+            e.printStackTrace();
+        } catch (InvocationTargetException e) {
+            e.printStackTrace();
+        } catch (IllegalAccessException e) {
+            e.printStackTrace();
+        }
+    }
+
+    private void init() {
+        // Create filters
+        messageFilter =
+            new AndFilter(
+                new FromMatchesFilter(room),
+                new MessageTypeFilter(Message.Type.groupchat));
+        messageFilter = new AndFilter(messageFilter, new PacketFilter() {
+            public boolean accept(Packet packet) {
+                Message msg = (Message) packet;
+                return msg.getBody() != null;
+            }
+        });
+        presenceFilter =
+            new AndFilter(new FromMatchesFilter(room), new PacketTypeFilter(Presence.class));
+
+        // Create a collector for incoming messages.
+        messageCollector = new ConnectionDetachedPacketCollector();
+
+        // Create a listener for subject updates.
+        PacketListener subjectListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                Message msg = (Message) packet;
+                // Update the room subject
+                subject = msg.getSubject();
+                // Fire event for subject updated listeners
+                fireSubjectUpdatedListeners(
+                    msg.getSubject(),
+                    msg.getFrom());
+
+            }
+        };
+
+        // Create a listener for all presence updates.
+        PacketListener presenceListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                Presence presence = (Presence) packet;
+                String from = presence.getFrom();
+                String myRoomJID = room + "/" + nickname;
+                boolean isUserStatusModification = presence.getFrom().equals(myRoomJID);
+                if (presence.getType() == Presence.Type.available) {
+                    Presence oldPresence = occupantsMap.put(from, presence);
+                    if (oldPresence != null) {
+                        // Get the previous occupant's affiliation & role
+                        MUCUser mucExtension = getMUCUserExtension(oldPresence);
+                        String oldAffiliation = mucExtension.getItem().getAffiliation();
+                        String oldRole = mucExtension.getItem().getRole();
+                        // Get the new occupant's affiliation & role
+                        mucExtension = getMUCUserExtension(presence);
+                        String newAffiliation = mucExtension.getItem().getAffiliation();
+                        String newRole = mucExtension.getItem().getRole();
+                        // Fire role modification events
+                        checkRoleModifications(oldRole, newRole, isUserStatusModification, from);
+                        // Fire affiliation modification events
+                        checkAffiliationModifications(
+                            oldAffiliation,
+                            newAffiliation,
+                            isUserStatusModification,
+                            from);
+                    }
+                    else {
+                        // A new occupant has joined the room
+                        if (!isUserStatusModification) {
+                            List<String> params = new ArrayList<String>();
+                            params.add(from);
+                            fireParticipantStatusListeners("joined", params);
+                        }
+                    }
+                }
+                else if (presence.getType() == Presence.Type.unavailable) {
+                    occupantsMap.remove(from);
+                    MUCUser mucUser = getMUCUserExtension(presence);
+                    if (mucUser != null && mucUser.getStatus() != null) {
+                        // Fire events according to the received presence code
+                        checkPresenceCode(
+                            mucUser.getStatus().getCode(),
+                            presence.getFrom().equals(myRoomJID),
+                            mucUser,
+                            from);
+                    } else {
+                        // An occupant has left the room
+                        if (!isUserStatusModification) {
+                            List<String> params = new ArrayList<String>();
+                            params.add(from);
+                            fireParticipantStatusListeners("left", params);
+                        }
+                    }
+                }
+            }
+        };
+
+        // Listens for all messages that include a MUCUser extension and fire the invitation
+        // rejection listeners if the message includes an invitation rejection.
+        PacketListener declinesListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                // Get the MUC User extension
+                MUCUser mucUser = getMUCUserExtension(packet);
+                // Check if the MUCUser informs that the invitee has declined the invitation
+                if (mucUser.getDecline() != null &&
+                        ((Message) packet).getType() != Message.Type.error) {
+                    // Fire event for invitation rejection listeners
+                    fireInvitationRejectionListeners(
+                        mucUser.getDecline().getFrom(),
+                        mucUser.getDecline().getReason());
+                }
+            }
+        };
+
+        PacketMultiplexListener packetMultiplexor = new PacketMultiplexListener(
+                messageCollector, presenceListener, subjectListener,
+                declinesListener);
+
+        roomListenerMultiplexor = RoomListenerMultiplexor.getRoomMultiplexor(connection);
+
+        roomListenerMultiplexor.addRoom(room, packetMultiplexor);
+    }
+
+    /**
+     * Fires notification events if the role of a room occupant has changed. If the occupant that
+     * changed his role is your occupant then the <code>UserStatusListeners</code> added to this
+     * <code>MultiUserChat</code> will be fired. On the other hand, if the occupant that changed
+     * his role is not yours then the <code>ParticipantStatusListeners</code> added to this
+     * <code>MultiUserChat</code> will be fired. The following table shows the events that will
+     * be fired depending on the previous and new role of the occupant.
+     *
+     * <pre>
+     * <table border="1">
+     * <tr><td><b>Old</b></td><td><b>New</b></td><td><b>Events</b></td></tr>
+     *
+     * <tr><td>None</td><td>Visitor</td><td>--</td></tr>
+     * <tr><td>Visitor</td><td>Participant</td><td>voiceGranted</td></tr>
+     * <tr><td>Participant</td><td>Moderator</td><td>moderatorGranted</td></tr>
+     *
+     * <tr><td>None</td><td>Participant</td><td>voiceGranted</td></tr>
+     * <tr><td>None</td><td>Moderator</td><td>voiceGranted + moderatorGranted</td></tr>
+     * <tr><td>Visitor</td><td>Moderator</td><td>voiceGranted + moderatorGranted</td></tr>
+     *
+     * <tr><td>Moderator</td><td>Participant</td><td>moderatorRevoked</td></tr>
+     * <tr><td>Participant</td><td>Visitor</td><td>voiceRevoked</td></tr>
+     * <tr><td>Visitor</td><td>None</td><td>kicked</td></tr>
+     *
+     * <tr><td>Moderator</td><td>Visitor</td><td>voiceRevoked + moderatorRevoked</td></tr>
+     * <tr><td>Moderator</td><td>None</td><td>kicked</td></tr>
+     * <tr><td>Participant</td><td>None</td><td>kicked</td></tr>
+     * </table>
+     * </pre>
+     *
+     * @param oldRole the previous role of the user in the room before receiving the new presence
+     * @param newRole the new role of the user in the room after receiving the new presence
+     * @param isUserModification whether the received presence is about your user in the room or not
+     * @param from the occupant whose role in the room has changed
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    private void checkRoleModifications(
+        String oldRole,
+        String newRole,
+        boolean isUserModification,
+        String from) {
+        // Voice was granted to a visitor
+        if (("visitor".equals(oldRole) || "none".equals(oldRole))
+            && "participant".equals(newRole)) {
+            if (isUserModification) {
+                fireUserStatusListeners("voiceGranted", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("voiceGranted", params);
+            }
+        }
+        // The participant's voice was revoked from the room
+        else if (
+            "participant".equals(oldRole)
+                && ("visitor".equals(newRole) || "none".equals(newRole))) {
+            if (isUserModification) {
+                fireUserStatusListeners("voiceRevoked", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("voiceRevoked", params);
+            }
+        }
+        // Moderator privileges were granted to a participant
+        if (!"moderator".equals(oldRole) && "moderator".equals(newRole)) {
+            if ("visitor".equals(oldRole) || "none".equals(oldRole)) {
+                if (isUserModification) {
+                    fireUserStatusListeners("voiceGranted", new Object[] {});
+                }
+                else {
+                    List<String> params = new ArrayList<String>();
+                    params.add(from);
+                    fireParticipantStatusListeners("voiceGranted", params);
+                }
+            }
+            if (isUserModification) {
+                fireUserStatusListeners("moderatorGranted", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("moderatorGranted", params);
+            }
+        }
+        // Moderator privileges were revoked from a participant
+        else if ("moderator".equals(oldRole) && !"moderator".equals(newRole)) {
+            if ("visitor".equals(newRole) || "none".equals(newRole)) {
+                if (isUserModification) {
+                    fireUserStatusListeners("voiceRevoked", new Object[] {});
+                }
+                else {
+                    List<String> params = new ArrayList<String>();
+                    params.add(from);
+                    fireParticipantStatusListeners("voiceRevoked", params);
+                }
+            }
+            if (isUserModification) {
+                fireUserStatusListeners("moderatorRevoked", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("moderatorRevoked", params);
+            }
+        }
+    }
+
+    /**
+     * Fires notification events if the affiliation of a room occupant has changed. If the
+     * occupant that changed his affiliation is your occupant then the
+     * <code>UserStatusListeners</code> added to this <code>MultiUserChat</code> will be fired.
+     * On the other hand, if the occupant that changed his affiliation is not yours then the
+     * <code>ParticipantStatusListeners</code> added to this <code>MultiUserChat</code> will be
+     * fired. The following table shows the events that will be fired depending on the previous
+     * and new affiliation of the occupant.
+     *
+     * <pre>
+     * <table border="1">
+     * <tr><td><b>Old</b></td><td><b>New</b></td><td><b>Events</b></td></tr>
+     *
+     * <tr><td>None</td><td>Member</td><td>membershipGranted</td></tr>
+     * <tr><td>Member</td><td>Admin</td><td>membershipRevoked + adminGranted</td></tr>
+     * <tr><td>Admin</td><td>Owner</td><td>adminRevoked + ownershipGranted</td></tr>
+     *
+     * <tr><td>None</td><td>Admin</td><td>adminGranted</td></tr>
+     * <tr><td>None</td><td>Owner</td><td>ownershipGranted</td></tr>
+     * <tr><td>Member</td><td>Owner</td><td>membershipRevoked + ownershipGranted</td></tr>
+     *
+     * <tr><td>Owner</td><td>Admin</td><td>ownershipRevoked + adminGranted</td></tr>
+     * <tr><td>Admin</td><td>Member</td><td>adminRevoked + membershipGranted</td></tr>
+     * <tr><td>Member</td><td>None</td><td>membershipRevoked</td></tr>
+     *
+     * <tr><td>Owner</td><td>Member</td><td>ownershipRevoked + membershipGranted</td></tr>
+     * <tr><td>Owner</td><td>None</td><td>ownershipRevoked</td></tr>
+     * <tr><td>Admin</td><td>None</td><td>adminRevoked</td></tr>
+     * <tr><td><i>Anyone</i></td><td>Outcast</td><td>banned</td></tr>
+     * </table>
+     * </pre>
+     *
+     * @param oldAffiliation the previous affiliation of the user in the room before receiving the
+     * new presence
+     * @param newAffiliation the new affiliation of the user in the room after receiving the new
+     * presence
+     * @param isUserModification whether the received presence is about your user in the room or not
+     * @param from the occupant whose role in the room has changed
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    private void checkAffiliationModifications(
+        String oldAffiliation,
+        String newAffiliation,
+        boolean isUserModification,
+        String from) {
+        // First check for revoked affiliation and then for granted affiliations. The idea is to
+        // first fire the "revoke" events and then fire the "grant" events.
+
+        // The user's ownership to the room was revoked
+        if ("owner".equals(oldAffiliation) && !"owner".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("ownershipRevoked", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("ownershipRevoked", params);
+            }
+        }
+        // The user's administrative privileges to the room were revoked
+        else if ("admin".equals(oldAffiliation) && !"admin".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("adminRevoked", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("adminRevoked", params);
+            }
+        }
+        // The user's membership to the room was revoked
+        else if ("member".equals(oldAffiliation) && !"member".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("membershipRevoked", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("membershipRevoked", params);
+            }
+        }
+
+        // The user was granted ownership to the room
+        if (!"owner".equals(oldAffiliation) && "owner".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("ownershipGranted", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("ownershipGranted", params);
+            }
+        }
+        // The user was granted administrative privileges to the room
+        else if (!"admin".equals(oldAffiliation) && "admin".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("adminGranted", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("adminGranted", params);
+            }
+        }
+        // The user was granted membership to the room
+        else if (!"member".equals(oldAffiliation) && "member".equals(newAffiliation)) {
+            if (isUserModification) {
+                fireUserStatusListeners("membershipGranted", new Object[] {});
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                fireParticipantStatusListeners("membershipGranted", params);
+            }
+        }
+    }
+
+    /**
+     * Fires events according to the received presence code.
+     *
+     * @param code
+     * @param isUserModification
+     * @param mucUser
+     * @param from
+     */
+    private void checkPresenceCode(
+        String code,
+        boolean isUserModification,
+        MUCUser mucUser,
+        String from) {
+        // Check if an occupant was kicked from the room
+        if ("307".equals(code)) {
+            // Check if this occupant was kicked
+            if (isUserModification) {
+                joined = false;
+
+                fireUserStatusListeners(
+                    "kicked",
+                    new Object[] { mucUser.getItem().getActor(), mucUser.getItem().getReason()});
+
+                // Reset occupant information.
+                occupantsMap.clear();
+                nickname = null;
+                userHasLeft();
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                params.add(mucUser.getItem().getActor());
+                params.add(mucUser.getItem().getReason());
+                fireParticipantStatusListeners("kicked", params);
+            }
+        }
+        // A user was banned from the room
+        else if ("301".equals(code)) {
+            // Check if this occupant was banned
+            if (isUserModification) {
+                joined = false;
+
+                fireUserStatusListeners(
+                    "banned",
+                    new Object[] { mucUser.getItem().getActor(), mucUser.getItem().getReason()});
+
+                // Reset occupant information.
+                occupantsMap.clear();
+                nickname = null;
+                userHasLeft();
+            }
+            else {
+                List<String> params = new ArrayList<String>();
+                params.add(from);
+                params.add(mucUser.getItem().getActor());
+                params.add(mucUser.getItem().getReason());
+                fireParticipantStatusListeners("banned", params);
+            }
+        }
+        // A user's membership was revoked from the room
+        else if ("321".equals(code)) {
+            // Check if this occupant's membership was revoked
+            if (isUserModification) {
+                joined = false;
+
+                fireUserStatusListeners("membershipRevoked", new Object[] {});
+
+                // Reset occupant information.
+                occupantsMap.clear();
+                nickname = null;
+                userHasLeft();
+            }
+        }
+        // A occupant has changed his nickname in the room
+        else if ("303".equals(code)) {
+            List<String> params = new ArrayList<String>();
+            params.add(from);
+            params.add(mucUser.getItem().getNick());
+            fireParticipantStatusListeners("nicknameChanged", params);
+        }
+    }
+
+    private void cleanup() {
+        try {
+            if (connection != null) {
+                roomListenerMultiplexor.removeRoom(room);
+                // Remove all the PacketListeners added to the connection by this chat
+                for (PacketListener connectionListener : connectionListeners) {
+                    connection.removePacketListener(connectionListener);
+                }
+            }
+        } catch (Exception e) {
+            // Do nothing
+        }
+    }
+
+    protected void finalize() throws Throwable {
+        cleanup();
+        super.finalize();
+    }
+
+    /**
+     * An InvitationsMonitor monitors a given connection to detect room invitations. Every
+     * time the InvitationsMonitor detects a new invitation it will fire the invitation listeners.
+     *
+     * @author Gaston Dombiak
+     */
+    private static class InvitationsMonitor implements ConnectionListener {
+        // We use a WeakHashMap so that the GC can collect the monitor when the
+        // connection is no longer referenced by any object.
+        // Note that when the InvitationsMonitor is used, i.e. when there are InvitationListeners, it will add a
+        // PacketListener to the Connection and therefore a strong reference from the Connection to the
+        // InvitationsMonior will exists, preventing it from beeing gc'ed. After the last InvitationListener is gone,
+        // the PacketListener will get removed (cancel()) allowing the garbage collection of the InvitationsMonitor
+        // instance.
+        private final static Map<Connection, WeakReference<InvitationsMonitor>> monitors =
+                new WeakHashMap<Connection, WeakReference<InvitationsMonitor>>();
+
+        // We don't use a synchronized List here because it would break the semantic of (add|remove)InvitationListener
+        private final List<InvitationListener> invitationsListeners =
+                new ArrayList<InvitationListener>();
+        private Connection connection;
+        private PacketFilter invitationFilter;
+        private PacketListener invitationPacketListener;
+
+        /**
+         * Returns a new or existing InvitationsMonitor for a given connection.
+         *
+         * @param conn the connection to monitor for room invitations.
+         * @return a new or existing InvitationsMonitor for a given connection.
+         */
+        public static InvitationsMonitor getInvitationsMonitor(Connection conn) {
+            synchronized (monitors) {
+                if (!monitors.containsKey(conn) || monitors.get(conn).get() == null) {
+                    // We need to use a WeakReference because the monitor references the
+                    // connection and this could prevent the GC from collecting the monitor
+                    // when no other object references the monitor
+                    InvitationsMonitor ivm = new InvitationsMonitor(conn);
+                    monitors.put(conn, new WeakReference<InvitationsMonitor>(ivm));
+                    return ivm;
+                }
+                // Return the InvitationsMonitor that monitors the connection
+                return monitors.get(conn).get();
+            }
+        }
+
+        /**
+         * Creates a new InvitationsMonitor that will monitor invitations received
+         * on a given connection.
+         * 
+         * @param connection the connection to monitor for possible room invitations
+         */
+        private InvitationsMonitor(Connection connection) {
+            this.connection = connection;
+        }
+
+        /**
+         * Adds a listener to invitation notifications. The listener will be fired anytime
+         * an invitation is received.<p>
+         *
+         * If this is the first monitor's listener then the monitor will be initialized in
+         * order to start listening to room invitations.
+         *
+         * @param listener an invitation listener.
+         */
+        public void addInvitationListener(InvitationListener listener) {
+            synchronized (invitationsListeners) {
+                // If this is the first monitor's listener then initialize the listeners
+                // on the connection to detect room invitations
+                if (invitationsListeners.size() == 0) {
+                    init();
+                }
+                if (!invitationsListeners.contains(listener)) {
+                    invitationsListeners.add(listener);
+                }
+            }
+        }
+
+        /**
+         * Removes a listener to invitation notifications. The listener will be fired anytime
+         * an invitation is received.<p>
+         *
+         * If there are no more listeners to notifiy for room invitations then the monitor will
+         * be stopped. As soon as a new listener is added to the monitor, the monitor will resume
+         * monitoring the connection for new room invitations.
+         *
+         * @param listener an invitation listener.
+         */
+        public void removeInvitationListener(InvitationListener listener) {
+            synchronized (invitationsListeners) {
+                if (invitationsListeners.contains(listener)) {
+                    invitationsListeners.remove(listener);
+                }
+                // If there are no more listeners to notifiy for room invitations
+                // then proceed to cancel/release this monitor
+                if (invitationsListeners.size() == 0) {
+                    cancel();
+                }
+            }
+        }
+
+        /**
+         * Fires invitation listeners.
+         */
+        private void fireInvitationListeners(String room, String inviter, String reason, String password,
+                                             Message message) {
+            InvitationListener[] listeners;
+            synchronized (invitationsListeners) {
+                listeners = new InvitationListener[invitationsListeners.size()];
+                invitationsListeners.toArray(listeners);
+            }
+            for (InvitationListener listener : listeners) {
+                listener.invitationReceived(connection, room, inviter, reason, password, message);
+            }
+        }
+
+        public void connectionClosed() {
+            cancel();
+        }
+
+        public void connectionClosedOnError(Exception e) {
+            // ignore              
+        }
+
+        public void reconnectingIn(int seconds) {
+            // ignore
+        }
+
+        public void reconnectionSuccessful() {
+            // ignore
+        }
+
+        public void reconnectionFailed(Exception e) {
+            // ignore
+        }
+
+        /**
+         * Initializes the listeners to detect received room invitations and to detect when the
+         * connection gets closed. As soon as a room invitation is received the invitations
+         * listeners will be fired. When the connection gets closed the monitor will remove
+         * his listeners on the connection.
+         */
+        private void init() {
+            // Listens for all messages that include a MUCUser extension and fire the invitation
+            // listeners if the message includes an invitation.
+            invitationFilter =
+                new PacketExtensionFilter("x", "http://jabber.org/protocol/muc#user");
+            invitationPacketListener = new PacketListener() {
+                public void processPacket(Packet packet) {
+                    // Get the MUCUser extension
+                    MUCUser mucUser =
+                        (MUCUser) packet.getExtension("x", "http://jabber.org/protocol/muc#user");
+                    // Check if the MUCUser extension includes an invitation
+                    if (mucUser.getInvite() != null &&
+                            ((Message) packet).getType() != Message.Type.error) {
+                        // Fire event for invitation listeners
+                        fireInvitationListeners(packet.getFrom(), mucUser.getInvite().getFrom(),
+                                mucUser.getInvite().getReason(), mucUser.getPassword(), (Message) packet);
+                    }
+                }
+            };
+            connection.addPacketListener(invitationPacketListener, invitationFilter);
+            // Add a listener to detect when the connection gets closed in order to
+            // cancel/release this monitor 
+            connection.addConnectionListener(this);
+        }
+
+        /**
+         * Cancels all the listeners that this InvitationsMonitor has added to the connection.
+         */
+        private void cancel() {
+            connection.removePacketListener(invitationPacketListener);
+            connection.removeConnectionListener(this);
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/Occupant.java b/src/org/jivesoftware/smackx/muc/Occupant.java
new file mode 100644
index 0000000..3b199a5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/Occupant.java
@@ -0,0 +1,121 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smackx.packet.MUCAdmin;
+import org.jivesoftware.smackx.packet.MUCUser;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * Represents the information about an occupant in a given room. The information will always have
+ * the affiliation and role of the occupant in the room. The full JID and nickname are optional.
+ *
+ * @author Gaston Dombiak
+ */
+public class Occupant {
+    // Fields that must have a value
+    private String affiliation;
+    private String role;
+    // Fields that may have a value
+    private String jid;
+    private String nick;
+
+    Occupant(MUCAdmin.Item item) {
+        super();
+        this.jid = item.getJid();
+        this.affiliation = item.getAffiliation();
+        this.role = item.getRole();
+        this.nick = item.getNick();
+    }
+
+    Occupant(Presence presence) {
+        super();
+        MUCUser mucUser = (MUCUser) presence.getExtension("x",
+                "http://jabber.org/protocol/muc#user");
+        MUCUser.Item item = mucUser.getItem();
+        this.jid = item.getJid();
+        this.affiliation = item.getAffiliation();
+        this.role = item.getRole();
+        // Get the nickname from the FROM attribute of the presence
+        this.nick = StringUtils.parseResource(presence.getFrom());
+    }
+
+    /**
+     * Returns the full JID of the occupant. If this information was extracted from a presence and
+     * the room is semi or full-anonymous then the answer will be null. On the other hand, if this
+     * information was obtained while maintaining the voice list or the moderator list then we will
+     * always have a full JID.
+     *
+     * @return the full JID of the occupant.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Returns the affiliation of the occupant. Possible affiliations are: "owner", "admin",
+     * "member", "outcast". This information will always be available.
+     *
+     * @return the affiliation of the occupant.
+     */
+    public String getAffiliation() {
+        return affiliation;
+    }
+
+    /**
+     * Returns the current role of the occupant in the room. This information will always be
+     * available.
+     *
+     * @return the current role of the occupant in the room.
+     */
+    public String getRole() {
+        return role;
+    }
+
+    /**
+     * Returns the current nickname of the occupant in the room. If this information was extracted
+     * from a presence then the answer will be null.
+     *
+     * @return the current nickname of the occupant in the room or null if this information was
+     *         obtained from a presence.
+     */
+    public String getNick() {
+        return nick;
+    }
+
+    public boolean equals(Object obj) {
+        if(!(obj instanceof Occupant)) {
+            return false;
+        }
+        Occupant occupant = (Occupant)obj;
+        return jid.equals(occupant.jid);
+    }
+
+    public int hashCode() {
+        int result;
+        result = affiliation.hashCode();
+        result = 17 * result + role.hashCode();
+        result = 17 * result + jid.hashCode();
+        result = 17 * result + (nick != null ? nick.hashCode() : 0);
+        return result;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/PacketMultiplexListener.java b/src/org/jivesoftware/smackx/muc/PacketMultiplexListener.java
new file mode 100644
index 0000000..c1863c2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/PacketMultiplexListener.java
@@ -0,0 +1,96 @@
+/**
+ * $RCSfile$
+ * $Revision: 2779 $
+ * $Date: 2005-09-05 17:00:45 -0300 (Mon, 05 Sep 2005) $
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.filter.MessageTypeFilter;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+
+/**
+ * The single <code>PacketListener</code> used by each {@link MultiUserChat}
+ * for all basic processing of presence, and message packets targeted to that chat.
+ *
+ * @author Larry Kirschner
+ */
+class PacketMultiplexListener implements PacketListener {
+
+    private static final PacketFilter MESSAGE_FILTER =
+            new MessageTypeFilter(Message.Type.groupchat);
+    private static final PacketFilter PRESENCE_FILTER = new PacketTypeFilter(Presence.class);
+    private static final PacketFilter SUBJECT_FILTER = new PacketFilter() {
+        public boolean accept(Packet packet) {
+            Message msg = (Message) packet;
+            return msg.getSubject() != null;
+        }
+    };
+    private static final PacketFilter DECLINES_FILTER =
+            new PacketExtensionFilter("x",
+                    "http://jabber.org/protocol/muc#user");
+
+    private ConnectionDetachedPacketCollector messageCollector;
+    private PacketListener presenceListener;
+    private PacketListener subjectListener;
+    private PacketListener declinesListener;
+
+    public PacketMultiplexListener(
+            ConnectionDetachedPacketCollector messageCollector,
+            PacketListener presenceListener,
+            PacketListener subjectListener, PacketListener declinesListener) {
+        if (messageCollector == null) {
+            throw new IllegalArgumentException("MessageCollector is null");
+        }
+        if (presenceListener == null) {
+            throw new IllegalArgumentException("Presence listener is null");
+        }
+        if (subjectListener == null) {
+            throw new IllegalArgumentException("Subject listener is null");
+        }
+        if (declinesListener == null) {
+            throw new IllegalArgumentException("Declines listener is null");
+        }
+        this.messageCollector = messageCollector;
+        this.presenceListener = presenceListener;
+        this.subjectListener = subjectListener;
+        this.declinesListener = declinesListener;
+    }
+
+    public void processPacket(Packet p) {
+        if (PRESENCE_FILTER.accept(p)) {
+            presenceListener.processPacket(p);
+        }
+        else if (MESSAGE_FILTER.accept(p)) {
+            messageCollector.processPacket(p);
+
+            if (SUBJECT_FILTER.accept(p)) {
+                subjectListener.processPacket(p);
+            }
+        }
+        else if (DECLINES_FILTER.accept(p)) {
+            declinesListener.processPacket(p);
+        }
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/ParticipantStatusListener.java b/src/org/jivesoftware/smackx/muc/ParticipantStatusListener.java
new file mode 100644
index 0000000..c3e248d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/ParticipantStatusListener.java
@@ -0,0 +1,179 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * A listener that is fired anytime a participant's status in a room is changed, such as the 
+ * user being kicked, banned, or granted admin permissions.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface ParticipantStatusListener {
+
+    /**
+     * Called when a new room occupant has joined the room. Note: Take in consideration that when
+     * you join a room you will receive the list of current occupants in the room. This message will
+     * be sent for each occupant.
+     *
+     * @param participant the participant that has just joined the room
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void joined(String participant);
+
+    /**
+     * Called when a room occupant has left the room on its own. This means that the occupant was
+     * neither kicked nor banned from the room.
+     *
+     * @param participant the participant that has left the room on its own.
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void left(String participant);
+
+    /**
+     * Called when a room participant has been kicked from the room. This means that the kicked 
+     * participant is no longer participating in the room.
+     * 
+     * @param participant the participant that was kicked from the room 
+     * (e.g. room@conference.jabber.org/nick).
+     * @param actor the moderator that kicked the occupant from the room (e.g. user@host.org).
+     * @param reason the reason provided by the actor to kick the occupant from the room.
+     */
+    public abstract void kicked(String participant, String actor, String reason);
+
+    /**
+     * Called when a moderator grants voice to a visitor. This means that the visitor 
+     * can now participate in the moderated room sending messages to all occupants.
+     * 
+     * @param participant the participant that was granted voice in the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void voiceGranted(String participant);
+
+    /**
+     * Called when a moderator revokes voice from a participant. This means that the participant 
+     * in the room was able to speak and now is a visitor that can't send messages to the room 
+     * occupants.
+     * 
+     * @param participant the participant that was revoked voice from the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void voiceRevoked(String participant);
+
+    /**
+     * Called when an administrator or owner banned a participant from the room. This means that 
+     * banned participant will no longer be able to join the room unless the ban has been removed.
+     * 
+     * @param participant the participant that was banned from the room 
+     * (e.g. room@conference.jabber.org/nick).
+     * @param actor the administrator that banned the occupant (e.g. user@host.org).
+     * @param reason the reason provided by the administrator to ban the occupant.
+     */
+    public abstract void banned(String participant, String actor, String reason);
+
+    /**
+     * Called when an administrator grants a user membership to the room. This means that the user 
+     * will be able to join the members-only room.
+     * 
+     * @param participant the participant that was granted membership in the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void membershipGranted(String participant);
+
+    /**
+     * Called when an administrator revokes a user membership to the room. This means that the 
+     * user will not be able to join the members-only room.
+     * 
+     * @param participant the participant that was revoked membership from the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void membershipRevoked(String participant);
+
+    /**
+     * Called when an administrator grants moderator privileges to a user. This means that the user 
+     * will be able to kick users, grant and revoke voice, invite other users, modify room's 
+     * subject plus all the partcipants privileges.
+     * 
+     * @param participant the participant that was granted moderator privileges in the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void moderatorGranted(String participant);
+
+    /**
+     * Called when an administrator revokes moderator privileges from a user. This means that the 
+     * user will no longer be able to kick users, grant and revoke voice, invite other users, 
+     * modify room's subject plus all the partcipants privileges.
+     * 
+     * @param participant the participant that was revoked moderator privileges in the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void moderatorRevoked(String participant);
+
+    /**
+     * Called when an owner grants a user ownership on the room. This means that the user 
+     * will be able to change defining room features as well as perform all administrative 
+     * functions.
+     * 
+     * @param participant the participant that was granted ownership on the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void ownershipGranted(String participant);
+
+    /**
+     * Called when an owner revokes a user ownership on the room. This means that the user 
+     * will no longer be able to change defining room features as well as perform all 
+     * administrative functions.
+     * 
+     * @param participant the participant that was revoked ownership on the room 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void ownershipRevoked(String participant);
+
+    /**
+     * Called when an owner grants administrator privileges to a user. This means that the user 
+     * will be able to perform administrative functions such as banning users and edit moderator 
+     * list.
+     * 
+     * @param participant the participant that was granted administrator privileges 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void adminGranted(String participant);
+
+    /**
+     * Called when an owner revokes administrator privileges from a user. This means that the user 
+     * will no longer be able to perform administrative functions such as banning users and edit 
+     * moderator list.
+     * 
+     * @param participant the participant that was revoked administrator privileges 
+     * (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void adminRevoked(String participant);
+
+    /**
+     * Called when a participant changed his/her nickname in the room. The new participant's 
+     * nickname will be informed with the next available presence.
+     * 
+     * @param participant the participant that was revoked administrator privileges
+     * (e.g. room@conference.jabber.org/nick).
+     * @param newNickname the new nickname that the participant decided to use.
+     */
+    public abstract void nicknameChanged(String participant, String newNickname);
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/RoomInfo.java b/src/org/jivesoftware/smackx/muc/RoomInfo.java
new file mode 100644
index 0000000..f97f544
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/RoomInfo.java
@@ -0,0 +1,190 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+
+import java.util.Iterator;
+
+/**
+ * Represents the room information that was discovered using Service Discovery. It's possible to
+ * obtain information about a room before joining the room but only for rooms that are public (i.e.
+ * rooms that may be discovered).
+ *
+ * @author Gaston Dombiak
+ */
+public class RoomInfo {
+
+    /**
+     * JID of the room. The node of the JID is commonly used as the ID of the room or name.
+     */
+    private String room;
+    /**
+     * Description of the room.
+     */
+    private String description = "";
+    /**
+     * Last known subject of the room.
+     */
+    private String subject = "";
+    /**
+     * Current number of occupants in the room.
+     */
+    private int occupantsCount = -1;
+    /**
+     * A room is considered members-only if an invitation is required in order to enter the room.
+     * Any user that is not a member of the room won't be able to join the room unless the user
+     * decides to register with the room (thus becoming a member).
+     */
+    private boolean membersOnly;
+    /**
+     * Moderated rooms enable only participants to speak. Users that join the room and aren't
+     * participants can't speak (they are just visitors).
+     */
+    private boolean moderated;
+    /**
+     * Every presence packet can include the JID of every occupant unless the owner deactives this
+     * configuration.
+     */
+    private boolean nonanonymous;
+    /**
+     * Indicates if users must supply a password to join the room.
+     */
+    private boolean passwordProtected;
+    /**
+     * Persistent rooms are saved to the database to make sure that rooms configurations can be
+     * restored in case the server goes down.
+     */
+    private boolean persistent;
+
+    RoomInfo(DiscoverInfo info) {
+        super();
+        this.room = info.getFrom();
+        // Get the information based on the discovered features
+        this.membersOnly = info.containsFeature("muc_membersonly");
+        this.moderated = info.containsFeature("muc_moderated");
+        this.nonanonymous = info.containsFeature("muc_nonanonymous");
+        this.passwordProtected = info.containsFeature("muc_passwordprotected");
+        this.persistent = info.containsFeature("muc_persistent");
+        // Get the information based on the discovered extended information
+        Form form = Form.getFormFrom(info);
+        if (form != null) {
+            FormField descField = form.getField("muc#roominfo_description");
+            this.description = ( descField == null || !(descField.getValues().hasNext()) )? "" : descField.getValues().next();
+
+            FormField subjField = form.getField("muc#roominfo_subject");
+            this.subject = ( subjField == null || !(subjField.getValues().hasNext()) ) ? "" : subjField.getValues().next();
+
+            FormField occCountField = form.getField("muc#roominfo_occupants");
+            this.occupantsCount = occCountField == null ? -1 : Integer.parseInt(occCountField.getValues()
+                    .next());
+        }
+    }
+
+    /**
+     * Returns the JID of the room whose information was discovered.
+     *
+     * @return the JID of the room whose information was discovered.
+     */
+    public String getRoom() {
+        return room;
+    }
+
+    /**
+     * Returns the discovered description of the room.
+     *
+     * @return the discovered description of the room.
+     */
+    public String getDescription() {
+        return description;
+    }
+
+    /**
+     * Returns the discovered subject of the room. The subject may be empty if the room does not
+     * have a subject.
+     *
+     * @return the discovered subject of the room.
+     */
+    public String getSubject() {
+        return subject;
+    }
+
+    /**
+     * Returns the discovered number of occupants that are currently in the room. If this
+     * information was not discovered (i.e. the server didn't send it) then a value of -1 will be
+     * returned.
+     *
+     * @return the number of occupants that are currently in the room or -1 if that information was
+     * not provided by the server.
+     */
+    public int getOccupantsCount() {
+        return occupantsCount;
+    }
+
+    /**
+     * Returns true if the room has restricted the access so that only members may enter the room.
+     *
+     * @return true if the room has restricted the access so that only members may enter the room.
+     */
+    public boolean isMembersOnly() {
+        return membersOnly;
+    }
+
+    /**
+     * Returns true if the room enabled only participants to speak. Occupants with a role of
+     * visitor won't be able to speak in the room.
+     *
+     * @return true if the room enabled only participants to speak.
+     */
+    public boolean isModerated() {
+        return moderated;
+    }
+
+    /**
+     * Returns true if presence packets will include the JID of every occupant.
+     *
+     * @return true if presence packets will include the JID of every occupant.
+     */
+    public boolean isNonanonymous() {
+        return nonanonymous;
+    }
+
+    /**
+     * Returns true if users musy provide a valid password in order to join the room.
+     *
+     * @return true if users musy provide a valid password in order to join the room.
+     */
+    public boolean isPasswordProtected() {
+        return passwordProtected;
+    }
+
+    /**
+     * Returns true if the room will persist after the last occupant have left the room.
+     *
+     * @return true if the room will persist after the last occupant have left the room.
+     */
+    public boolean isPersistent() {
+        return persistent;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/RoomListenerMultiplexor.java b/src/org/jivesoftware/smackx/muc/RoomListenerMultiplexor.java
new file mode 100644
index 0000000..6f8bf05
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/RoomListenerMultiplexor.java
@@ -0,0 +1,227 @@
+/**
+ * $RCSfile$
+ * $Revision: 2779 $
+ * $Date: 2005-09-05 17:00:45 -0300 (Mon, 05 Sep 2005) $
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.lang.ref.WeakReference;
+import java.util.Map;
+import java.util.WeakHashMap;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * A <code>RoomListenerMultiplexor</code> multiplexes incoming packets on
+ * a <code>Connection</code> using a single listener/filter pair.
+ * A single <code>RoomListenerMultiplexor</code> is created for each
+ * {@link org.jivesoftware.smack.Connection} that has joined MUC rooms
+ * within its session.
+ *
+ * @author Larry Kirschner
+ */
+class RoomListenerMultiplexor implements ConnectionListener {
+
+    // We use a WeakHashMap so that the GC can collect the monitor when the
+    // connection is no longer referenced by any object.
+    private static final Map<Connection, WeakReference<RoomListenerMultiplexor>> monitors =
+            new WeakHashMap<Connection, WeakReference<RoomListenerMultiplexor>>();
+
+    private Connection connection;
+    private RoomMultiplexFilter filter;
+    private RoomMultiplexListener listener;
+
+    /**
+     * Returns a new or existing RoomListenerMultiplexor for a given connection.
+     *
+     * @param conn the connection to monitor for room invitations.
+     * @return a new or existing RoomListenerMultiplexor for a given connection.
+     */
+    public static RoomListenerMultiplexor getRoomMultiplexor(Connection conn) {
+        synchronized (monitors) {
+            if (!monitors.containsKey(conn) || monitors.get(conn).get() == null) {
+                RoomListenerMultiplexor rm = new RoomListenerMultiplexor(conn, new RoomMultiplexFilter(),
+                        new RoomMultiplexListener());
+
+                rm.init();
+
+                // We need to use a WeakReference because the monitor references the
+                // connection and this could prevent the GC from collecting the monitor
+                // when no other object references the monitor
+                monitors.put(conn, new WeakReference<RoomListenerMultiplexor>(rm));
+            }
+            // Return the InvitationsMonitor that monitors the connection
+            return monitors.get(conn).get();
+        }
+    }
+
+    /**
+     * All access should be through
+     * the static method {@link #getRoomMultiplexor(Connection)}.
+     */
+    private RoomListenerMultiplexor(Connection connection, RoomMultiplexFilter filter,
+            RoomMultiplexListener listener) {
+        if (connection == null) {
+            throw new IllegalArgumentException("Connection is null");
+        }
+        if (filter == null) {
+            throw new IllegalArgumentException("Filter is null");
+        }
+        if (listener == null) {
+            throw new IllegalArgumentException("Listener is null");
+        }
+        this.connection = connection;
+        this.filter = filter;
+        this.listener = listener;
+    }
+
+    public void addRoom(String address, PacketMultiplexListener roomListener) {
+        filter.addRoom(address);
+        listener.addRoom(address, roomListener);
+    }
+
+    public void connectionClosed() {
+        cancel();
+    }
+
+    public void connectionClosedOnError(Exception e) {
+        cancel();
+    }
+
+    public void reconnectingIn(int seconds) {
+        // ignore
+    }
+
+    public void reconnectionSuccessful() {
+        // ignore
+    }
+
+    public void reconnectionFailed(Exception e) {
+        // ignore
+    }
+
+    /**
+     * Initializes the listeners to detect received room invitations and to detect when the
+     * connection gets closed. As soon as a room invitation is received the invitations
+     * listeners will be fired. When the connection gets closed the monitor will remove
+     * his listeners on the connection.
+     */
+    public void init() {
+        connection.addConnectionListener(this);
+        connection.addPacketListener(listener, filter);
+    }
+
+    public void removeRoom(String address) {
+        filter.removeRoom(address);
+        listener.removeRoom(address);
+    }
+
+    /**
+     * Cancels all the listeners that this InvitationsMonitor has added to the connection.
+     */
+    private void cancel() {
+        connection.removeConnectionListener(this);
+        connection.removePacketListener(listener);
+    }
+
+    /**
+     * The single <code>Connection</code>-level <code>PacketFilter</code> used by a {@link RoomListenerMultiplexor}
+     * for all muc chat rooms on an <code>Connection</code>.
+     * Each time a muc chat room is added to/removed from an
+     * <code>Connection</code> the address for that chat room
+     * is added to/removed from that <code>Connection</code>'s
+     * <code>RoomMultiplexFilter</code>.
+     */
+    private static class RoomMultiplexFilter implements PacketFilter {
+
+        private Map<String, String> roomAddressTable = new ConcurrentHashMap<String, String>();
+
+        public boolean accept(Packet p) {
+            String from = p.getFrom();
+            if (from == null) {
+                return false;
+            }
+            return roomAddressTable.containsKey(StringUtils.parseBareAddress(from).toLowerCase());
+        }
+
+        public void addRoom(String address) {
+            if (address == null) {
+                return;
+            }
+            roomAddressTable.put(address.toLowerCase(), address);
+        }
+
+        public void removeRoom(String address) {
+            if (address == null) {
+                return;
+            }
+            roomAddressTable.remove(address.toLowerCase());
+        }
+    }
+
+    /**
+     * The single <code>Connection</code>-level <code>PacketListener</code>
+     * used by a {@link RoomListenerMultiplexor}
+     * for all muc chat rooms on an <code>Connection</code>.
+     * Each time a muc chat room is added to/removed from an
+     * <code>Connection</code> the address and listener for that chat room
+     * are added to/removed from that <code>Connection</code>'s
+     * <code>RoomMultiplexListener</code>.
+     *
+     * @author Larry Kirschner
+     */
+    private static class RoomMultiplexListener implements PacketListener {
+
+        private Map<String, PacketMultiplexListener> roomListenersByAddress =
+                new ConcurrentHashMap<String, PacketMultiplexListener>();
+
+        public void processPacket(Packet p) {
+            String from = p.getFrom();
+            if (from == null) {
+                return;
+            }
+
+            PacketMultiplexListener listener =
+                    roomListenersByAddress.get(StringUtils.parseBareAddress(from).toLowerCase());
+
+            if (listener != null) {
+                listener.processPacket(p);
+            }
+        }
+
+        public void addRoom(String address, PacketMultiplexListener listener) {
+            if (address == null) {
+                return;
+            }
+            roomListenersByAddress.put(address.toLowerCase(), listener);
+        }
+
+        public void removeRoom(String address) {
+            if (address == null) {
+                return;
+            }
+            roomListenersByAddress.remove(address.toLowerCase());
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/muc/SubjectUpdatedListener.java b/src/org/jivesoftware/smackx/muc/SubjectUpdatedListener.java
new file mode 100644
index 0000000..3a2deab
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/SubjectUpdatedListener.java
@@ -0,0 +1,38 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * A listener that is fired anytime a MUC room changes its subject.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface SubjectUpdatedListener {
+
+    /**
+     * Called when a MUC room has changed its subject.
+     * 
+     * @param subject the new room's subject.
+     * @param from the user that changed the room's subject (e.g. room@conference.jabber.org/nick).
+     */
+    public abstract void subjectUpdated(String subject, String from);
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/UserStatusListener.java b/src/org/jivesoftware/smackx/muc/UserStatusListener.java
new file mode 100644
index 0000000..27f0f58
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/UserStatusListener.java
@@ -0,0 +1,127 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.muc;
+
+/**
+ * A listener that is fired anytime your participant's status in a room is changed, such as the 
+ * user being kicked, banned, or granted admin permissions.
+ * 
+ * @author Gaston Dombiak
+ */
+public interface UserStatusListener {
+
+    /**
+     * Called when a moderator kicked your user from the room. This means that you are no longer
+     * participanting in the room.
+     * 
+     * @param actor the moderator that kicked your user from the room (e.g. user@host.org).
+     * @param reason the reason provided by the actor to kick you from the room.
+     */
+    public abstract void kicked(String actor, String reason);
+
+    /**
+     * Called when a moderator grants voice to your user. This means that you were a visitor in 
+     * the moderated room before and now you can participate in the room by sending messages to 
+     * all occupants.
+     * 
+     */
+    public abstract void voiceGranted();
+
+    /**
+     * Called when a moderator revokes voice from your user. This means that you were a 
+     * participant in the room able to speak and now you are a visitor that can't send 
+     * messages to the room occupants.
+     * 
+     */
+    public abstract void voiceRevoked();
+
+    /**
+     * Called when an administrator or owner banned your user from the room. This means that you 
+     * will no longer be able to join the room unless the ban has been removed.
+     * 
+     * @param actor the administrator that banned your user (e.g. user@host.org).
+     * @param reason the reason provided by the administrator to banned you.
+     */
+    public abstract void banned(String actor, String reason);
+
+    /**
+     * Called when an administrator grants your user membership to the room. This means that you 
+     * will be able to join the members-only room. 
+     * 
+     */
+    public abstract void membershipGranted();
+
+    /**
+     * Called when an administrator revokes your user membership to the room. This means that you 
+     * will not be able to join the members-only room.
+     * 
+     */
+    public abstract void membershipRevoked();
+
+    /**
+     * Called when an administrator grants moderator privileges to your user. This means that you 
+     * will be able to kick users, grant and revoke voice, invite other users, modify room's 
+     * subject plus all the partcipants privileges.
+     * 
+     */
+    public abstract void moderatorGranted();
+
+    /**
+     * Called when an administrator revokes moderator privileges from your user. This means that 
+     * you will no longer be able to kick users, grant and revoke voice, invite other users, 
+     * modify room's subject plus all the partcipants privileges.
+     * 
+     */
+    public abstract void moderatorRevoked();
+
+    /**
+     * Called when an owner grants to your user ownership on the room. This means that you 
+     * will be able to change defining room features as well as perform all administrative 
+     * functions.
+     * 
+     */
+    public abstract void ownershipGranted();
+
+    /**
+     * Called when an owner revokes from your user ownership on the room. This means that you 
+     * will no longer be able to change defining room features as well as perform all 
+     * administrative functions.
+     * 
+     */
+    public abstract void ownershipRevoked();
+
+    /**
+     * Called when an owner grants administrator privileges to your user. This means that you 
+     * will be able to perform administrative functions such as banning users and edit moderator 
+     * list.
+     * 
+     */
+    public abstract void adminGranted();
+
+    /**
+     * Called when an owner revokes administrator privileges from your user. This means that you 
+     * will no longer be able to perform administrative functions such as banning users and edit 
+     * moderator list.
+     * 
+     */
+    public abstract void adminRevoked();
+
+}
diff --git a/src/org/jivesoftware/smackx/muc/package.html b/src/org/jivesoftware/smackx/muc/package.html
new file mode 100644
index 0000000..dcfaeaa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/muc/package.html
@@ -0,0 +1 @@
+<body>Classes and Interfaces that implement Multi-User Chat (MUC).</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/package.html b/src/org/jivesoftware/smackx/package.html
new file mode 100644
index 0000000..d574a2a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/package.html
@@ -0,0 +1 @@
+<body>Smack extensions API.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/packet/AdHocCommandData.java b/src/org/jivesoftware/smackx/packet/AdHocCommandData.java
new file mode 100755
index 0000000..bceffcd
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/AdHocCommandData.java
@@ -0,0 +1,279 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2008 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.commands.AdHocCommand;
+import org.jivesoftware.smackx.commands.AdHocCommand.Action;
+import org.jivesoftware.smackx.commands.AdHocCommand.SpecificErrorCondition;
+import org.jivesoftware.smackx.commands.AdHocCommandNote;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Represents the state and the request of the execution of an adhoc command.
+ * 
+ * @author Gabriel Guardincerri
+ */
+public class AdHocCommandData extends IQ {
+
+    /* JID of the command host */
+    private String id;
+
+    /* Command name */
+    private String name;
+
+    /* Command identifier */
+    private String node;
+
+    /* Unique ID of the execution */
+    private String sessionID;
+
+    private List<AdHocCommandNote> notes = new ArrayList<AdHocCommandNote>();
+
+    private DataForm form;
+
+    /* Action request to be executed */
+    private AdHocCommand.Action action;
+
+    /* Current execution status */
+    private AdHocCommand.Status status;
+
+    private ArrayList<AdHocCommand.Action> actions = new ArrayList<AdHocCommand.Action>();
+
+    private AdHocCommand.Action executeAction;
+
+    private String lang;
+
+    public AdHocCommandData() {
+    }
+
+    @Override
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<command xmlns=\"http://jabber.org/protocol/commands\"");
+        buf.append(" node=\"").append(node).append("\"");
+        if (sessionID != null) {
+            if (!sessionID.equals("")) {
+                buf.append(" sessionid=\"").append(sessionID).append("\"");
+            }
+        }
+        if (status != null) {
+            buf.append(" status=\"").append(status).append("\"");
+        }
+        if (action != null) {
+            buf.append(" action=\"").append(action).append("\"");
+        }
+
+        if (lang != null) {
+            if (!lang.equals("")) {
+                buf.append(" lang=\"").append(lang).append("\"");
+            }
+        }
+        buf.append(">");
+
+        if (getType() == Type.RESULT) {
+            buf.append("<actions");
+
+            if (executeAction != null) {
+                buf.append(" execute=\"").append(executeAction).append("\"");
+            }
+            if (actions.size() == 0) {
+                buf.append("/>");
+            } else {
+                buf.append(">");
+
+                for (AdHocCommand.Action action : actions) {
+                    buf.append("<").append(action).append("/>");
+                }
+                buf.append("</actions>");
+            }
+        }
+
+        if (form != null) {
+            buf.append(form.toXML());
+        }
+
+        for (AdHocCommandNote note : notes) {
+            buf.append("<note type=\"").append(note.getType().toString()).append("\">");
+            buf.append(note.getValue());
+            buf.append("</note>");
+        }
+
+        // TODO ERRORS
+//        if (getError() != null) {
+//            buf.append(getError().toXML());
+//        }
+
+        buf.append("</command>");
+        return buf.toString();
+    }
+
+    /**
+     * Returns the JID of the command host.
+     *
+     * @return the JID of the command host.
+     */
+    public String getId() {
+        return id;
+    }
+
+    public void setId(String id) {
+        this.id = id;
+    }
+
+    /**
+     * Returns the human name of the command
+     *
+     * @return the name of the command.
+     */
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    /**
+     * Returns the identifier of the command
+     *
+     * @return the node.
+     */
+    public String getNode() {
+        return node;
+    }
+
+    public void setNode(String node) {
+        this.node = node;
+    }
+
+    /**
+     * Returns the list of notes that the command has.
+     *
+     * @return the notes.
+     */
+    public List<AdHocCommandNote> getNotes() {
+        return notes;
+    }
+
+    public void addNote(AdHocCommandNote note) {
+        this.notes.add(note);
+    }
+
+    public void remveNote(AdHocCommandNote note) {
+        this.notes.remove(note);
+    }
+
+    /**
+     * Returns the form of the command.
+     *
+     * @return the data form associated with the command.
+     */
+    public DataForm getForm() {
+        return form;
+    }
+
+    public void setForm(DataForm form) {
+        this.form = form;
+    }
+
+    /**
+     * Returns the action to execute. The action is set only on a request.
+     *
+     * @return the action to execute.
+     */
+    public AdHocCommand.Action getAction() {
+        return action;
+    }
+
+    public void setAction(AdHocCommand.Action action) {
+        this.action = action;
+    }
+
+    /**
+     * Returns the status of the execution.
+     *
+     * @return the status.
+     */
+    public AdHocCommand.Status getStatus() {
+        return status;
+    }
+
+    public void setStatus(AdHocCommand.Status status) {
+        this.status = status;
+    }
+
+    public List<Action> getActions() {
+        return actions;
+    }
+
+    public void addAction(Action action) {
+        actions.add(action);
+    }
+
+    public void setExecuteAction(Action executeAction) {
+        this.executeAction = executeAction;
+    }
+
+    public Action getExecuteAction() {
+        return executeAction;
+    }
+
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public static class SpecificError implements PacketExtension {
+
+        public static final String namespace = "http://jabber.org/protocol/commands";
+        
+        public SpecificErrorCondition condition;
+        
+        public SpecificError(SpecificErrorCondition condition) {
+            this.condition = condition;
+        }
+        
+        public String getElementName() {
+            return condition.toString();
+        }
+        public String getNamespace() {
+            return namespace;
+        }
+
+        public SpecificErrorCondition getCondition() {
+            return condition;
+        }
+        
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<").append(getElementName());
+            buf.append(" xmlns=\"").append(getNamespace()).append("\"/>");
+            return buf.toString();
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/packet/AttentionExtension.java b/src/org/jivesoftware/smackx/packet/AttentionExtension.java
new file mode 100644
index 0000000..d86fa41
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/AttentionExtension.java
@@ -0,0 +1,100 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2010 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * A PacketExtension that implements XEP-0224: Attention
+ * 
+ * This extension is expected to be added to message stanzas of type 'headline.'
+ * Please refer to the XEP for more implementation guidelines.
+ * 
+ * @author Guus der Kinderen, guus.der.kinderen@gmail.com
+ * @see <a
+ *      href="http://xmpp.org/extensions/xep-0224.html">XEP-0224:&nbsp;Attention</a>
+ */
+public class AttentionExtension implements PacketExtension {
+
+    /**
+     * The XML element name of an 'attention' extension.
+     */
+    public static final String ELEMENT_NAME = "attention";
+
+    /**
+     * The namespace that qualifies the XML element of an 'attention' extension.
+     */
+    public static final String NAMESPACE = "urn:xmpp:attention:0";
+
+    /*
+     * (non-Javadoc)
+     * 
+     * @see org.jivesoftware.smack.packet.PacketExtension#getElementName()
+     */
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    /*
+     * (non-Javadoc)
+     * 
+     * @see org.jivesoftware.smack.packet.PacketExtension#getNamespace()
+     */
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    /*
+     * (non-Javadoc)
+     * 
+     * @see org.jivesoftware.smack.packet.PacketExtension#toXML()
+     */
+    public String toXML() {
+        final StringBuilder sb = new StringBuilder();
+        sb.append("<").append(getElementName()).append(" xmlns=\"").append(
+                getNamespace()).append("\"/>");
+        return sb.toString();
+    }
+
+    /**
+     * A {@link PacketExtensionProvider} for the {@link AttentionExtension}. As
+     * Attention elements have no state/information other than the element name
+     * and namespace, this implementation simply returns new instances of
+     * {@link AttentionExtension}.
+     * 
+     * @author Guus der Kinderen, guus.der.kinderen@gmail.com
+s     */
+    public static class Provider implements PacketExtensionProvider {
+
+        /*
+         * (non-Javadoc)
+         * 
+         * @see
+         * org.jivesoftware.smack.provider.PacketExtensionProvider#parseExtension
+         * (org.xmlpull.v1.XmlPullParser)
+         */
+        public PacketExtension parseExtension(XmlPullParser arg0)
+                throws Exception {
+            return new AttentionExtension();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/ChatStateExtension.java b/src/org/jivesoftware/smackx/packet/ChatStateExtension.java
new file mode 100644
index 0000000..ecc6acc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/ChatStateExtension.java
@@ -0,0 +1,73 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smackx.ChatState;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Represents a chat state which is an extension to message packets which is used to indicate
+ * the current status of a chat participant.
+ *
+ * @author Alexander Wenckus
+ * @see org.jivesoftware.smackx.ChatState
+ */
+public class ChatStateExtension implements PacketExtension {
+
+    private ChatState state;
+
+    /**
+     * Default constructor. The argument provided is the state that the extension will represent.
+     *
+     * @param state the state that the extension represents.
+     */
+    public ChatStateExtension(ChatState state) {
+        this.state = state;
+    }
+
+    public String getElementName() {
+        return state.name();
+    }
+
+    public String getNamespace() {
+        return "http://jabber.org/protocol/chatstates";
+    }
+
+    public String toXML() {
+        return "<" + getElementName() + " xmlns=\"" + getNamespace() + "\" />";
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            ChatState state;
+            try {
+                state = ChatState.valueOf(parser.getName());
+            }
+            catch (Exception ex) {
+                state = ChatState.active;
+            }
+            return new ChatStateExtension(state);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/DataForm.java b/src/org/jivesoftware/smackx/packet/DataForm.java
new file mode 100644
index 0000000..4d12892
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DataForm.java
@@ -0,0 +1,312 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents a form that could be use for gathering data as well as for reporting data
+ * returned from a search.
+ *
+ * @author Gaston Dombiak
+ */
+public class DataForm implements PacketExtension {
+
+    private String type;
+    private String title;
+    private List<String> instructions = new ArrayList<String>();
+    private ReportedData reportedData;
+    private final List<Item> items = new ArrayList<Item>();
+    private final List<FormField> fields = new ArrayList<FormField>();
+    
+    public DataForm(String type) {
+        this.type = type;
+    }
+    
+    /**
+     * Returns the meaning of the data within the context. The data could be part of a form
+     * to fill out, a form submission or data results.<p>
+     * 
+     * Possible form types are:
+     * <ul>
+     *  <li>form -> This packet contains a form to fill out. Display it to the user (if your 
+     * program can).</li>
+     *  <li>submit -> The form is filled out, and this is the data that is being returned from 
+     * the form.</li>
+     *  <li>cancel -> The form was cancelled. Tell the asker that piece of information.</li>
+     *  <li>result -> Data results being returned from a search, or some other query.</li>
+     * </ul>
+     * 
+     * @return the form's type.
+     */
+    public String getType() {
+        return type; 
+    }
+    
+    /**
+     * Returns the description of the data. It is similar to the title on a web page or an X 
+     * window.  You can put a <title/> on either a form to fill out, or a set of data results.
+     * 
+     * @return description of the data.
+     */
+    public String getTitle() {
+        return title;
+    }
+
+    /**
+     * Returns an Iterator for the list of instructions that explain how to fill out the form and 
+     * what the form is about. The dataform could include multiple instructions since each 
+     * instruction could not contain newlines characters. Join the instructions together in order 
+     * to show them to the user.    
+     * 
+     * @return an Iterator for the list of instructions that explain how to fill out the form.
+     */
+    public Iterator<String> getInstructions() {
+        synchronized (instructions) {
+            return Collections.unmodifiableList(new ArrayList<String>(instructions)).iterator();
+        }
+    }
+
+    /**
+     * Returns the fields that will be returned from a search.
+     * 
+     * @return fields that will be returned from a search.
+     */
+    public ReportedData getReportedData() {
+        return reportedData;
+    }
+
+    /**
+     * Returns an Iterator for the items returned from a search.
+     *
+     * @return an Iterator for the items returned from a search.
+     */
+    public Iterator<Item> getItems() {
+        synchronized (items) {
+            return Collections.unmodifiableList(new ArrayList<Item>(items)).iterator();
+        }
+    }
+
+    /**
+     * Returns an Iterator for the fields that are part of the form.
+     *
+     * @return an Iterator for the fields that are part of the form.
+     */
+    public Iterator<FormField> getFields() {
+        synchronized (fields) {
+            return Collections.unmodifiableList(new ArrayList<FormField>(fields)).iterator();
+        }
+    }
+
+    public String getElementName() {
+        return Form.ELEMENT;
+    }
+
+    public String getNamespace() {
+        return Form.NAMESPACE;
+    }
+
+    /**
+     * Sets the description of the data. It is similar to the title on a web page or an X window.
+     * You can put a <title/> on either a form to fill out, or a set of data results.
+     * 
+     * @param title description of the data.
+     */
+    public void setTitle(String title) {
+        this.title = title;
+    }
+
+    /**
+     * Sets the list of instructions that explain how to fill out the form and what the form is 
+     * about. The dataform could include multiple instructions since each instruction could not 
+     * contain newlines characters. 
+     * 
+     * @param instructions list of instructions that explain how to fill out the form.
+     */
+    public void setInstructions(List<String> instructions) {
+        this.instructions = instructions;
+    }
+
+    /**
+     * Sets the fields that will be returned from a search.
+     * 
+     * @param reportedData the fields that will be returned from a search.
+     */
+    public void setReportedData(ReportedData reportedData) {
+        this.reportedData = reportedData;
+    }
+
+    /**
+     * Adds a new field as part of the form.
+     * 
+     * @param field the field to add to the form.
+     */
+    public void addField(FormField field) {
+        synchronized (fields) {
+            fields.add(field);
+        }
+    }
+    
+    /**
+     * Adds a new instruction to the list of instructions that explain how to fill out the form 
+     * and what the form is about. The dataform could include multiple instructions since each 
+     * instruction could not contain newlines characters. 
+     * 
+     * @param instruction the new instruction that explain how to fill out the form.
+     */
+    public void addInstruction(String instruction) {
+        synchronized (instructions) {
+            instructions.add(instruction);
+        }
+    }
+
+    /**
+     * Adds a new item returned from a search.
+     * 
+     * @param item the item returned from a search.
+     */
+    public void addItem(Item item) {
+        synchronized (items) {
+            items.add(item);
+        }
+    }
+
+    /**
+     * Returns true if this DataForm has at least one FORM_TYPE field which is
+     * hidden. This method is used for sanity checks.
+     *
+     * @return
+     */
+    public boolean hasHiddenFormTypeField() {
+        boolean found = false;
+        for (FormField f : fields) {
+            if (f.getVariable().equals("FORM_TYPE") && f.getType() != null && f.getType().equals("hidden"))
+                found = true;
+        }
+        return found;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\" type=\"" + getType() +"\">");
+        if (getTitle() != null) {
+            buf.append("<title>").append(getTitle()).append("</title>");
+        }
+        for (Iterator<String> it=getInstructions(); it.hasNext();) {
+            buf.append("<instructions>").append(it.next()).append("</instructions>");
+        }
+        // Append the list of fields returned from a search
+        if (getReportedData() != null) {
+            buf.append(getReportedData().toXML());
+        }
+        // Loop through all the items returned from a search and append them to the string buffer
+        for (Iterator<Item> i = getItems(); i.hasNext();) {
+            Item item = i.next();
+            buf.append(item.toXML());
+        }
+        // Loop through all the form fields and append them to the string buffer
+        for (Iterator<FormField> i = getFields(); i.hasNext();) {
+            FormField field = i.next();
+            buf.append(field.toXML());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * 
+     * Represents the fields that will be returned from a search. This information is useful when 
+     * you try to use the jabber:iq:search namespace to return dynamic form information.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class ReportedData {
+        private List<FormField> fields = new ArrayList<FormField>();
+        
+        public ReportedData(List<FormField> fields) {
+            this.fields = fields;
+        }
+        
+        /**
+         * Returns the fields returned from a search.
+         * 
+         * @return the fields returned from a search.
+         */
+        public Iterator<FormField> getFields() {
+            return Collections.unmodifiableList(new ArrayList<FormField>(fields)).iterator();
+        }
+        
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<reported>");
+            // Loop through all the form items and append them to the string buffer
+            for (Iterator<FormField> i = getFields(); i.hasNext();) {
+                FormField field = i.next();
+                buf.append(field.toXML());
+            }
+            buf.append("</reported>");
+            return buf.toString();
+        }
+    }
+    
+    /**
+     * 
+     * Represents items of reported data.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Item {
+        private List<FormField> fields = new ArrayList<FormField>();
+        
+        public Item(List<FormField> fields) {
+            this.fields = fields;
+        }
+        
+        /**
+         * Returns the fields that define the data that goes with the item.
+         * 
+         * @return the fields that define the data that goes with the item.
+         */
+        public Iterator<FormField> getFields() {
+            return Collections.unmodifiableList(new ArrayList<FormField>(fields)).iterator();
+        }
+        
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item>");
+            // Loop through all the form items and append them to the string buffer
+            for (Iterator<FormField> i = getFields(); i.hasNext();) {
+                FormField field = i.next();
+                buf.append(field.toXML());
+            }
+            buf.append("</item>");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/DefaultPrivateData.java b/src/org/jivesoftware/smackx/packet/DefaultPrivateData.java
new file mode 100644
index 0000000..b58fc6c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DefaultPrivateData.java
@@ -0,0 +1,137 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+/**
+ * Default implementation of the PrivateData interface. Unless a PrivateDataProvider
+ * is registered with the PrivateDataManager class, instances of this class will be
+ * returned when getting private data.<p>
+ *
+ * This class provides a very simple representation of an XML sub-document. Each element
+ * is a key in a Map with its CDATA being the value. For example, given the following
+ * XML sub-document:
+ *
+ * <pre>
+ * &lt;foo xmlns="http://bar.com"&gt;
+ *     &lt;color&gt;blue&lt;/color&gt;
+ *     &lt;food&gt;pizza&lt;/food&gt;
+ * &lt;/foo&gt;</pre>
+ *
+ * In this case, getValue("color") would return "blue", and getValue("food") would
+ * return "pizza". This parsing mechanism mechanism is very simplistic and will not work
+ * as desired in all cases (for example, if some of the elements have attributes. In those
+ * cases, a custom {@link org.jivesoftware.smackx.provider.PrivateDataProvider} should be used.
+ *
+ * @author Matt Tucker
+ */
+public class DefaultPrivateData implements PrivateData {
+
+    private String elementName;
+    private String namespace;
+    private Map<String, String> map;
+
+    /**
+     * Creates a new generic private data object.
+     *
+     * @param elementName the name of the element of the XML sub-document.
+     * @param namespace the namespace of the element.
+     */
+    public DefaultPrivateData(String elementName, String namespace) {
+        this.elementName = elementName;
+        this.namespace = namespace;
+    }
+
+     /**
+     * Returns the XML element name of the private data sub-packet root element.
+     *
+     * @return the XML element name of the packet extension.
+     */
+    public String getElementName() {
+        return elementName;
+    }
+
+    /**
+     * Returns the XML namespace of the private data sub-packet root element.
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return namespace;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(elementName).append(" xmlns=\"").append(namespace).append("\">");
+        for (Iterator<String> i=getNames(); i.hasNext(); ) {
+            String name = i.next();
+            String value = getValue(name);
+            buf.append("<").append(name).append(">");
+            buf.append(value);
+            buf.append("</").append(name).append(">");
+        }
+        buf.append("</").append(elementName).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Returns an Iterator for the names that can be used to get
+     * values of the private data.
+     *
+     * @return an Iterator for the names.
+     */
+    public synchronized Iterator<String> getNames() {
+        if (map == null) {
+            return Collections.<String>emptyList().iterator();
+        }
+        return Collections.unmodifiableSet(map.keySet()).iterator();
+    }
+
+    /**
+     * Returns a value given a name.
+     *
+     * @param name the name.
+     * @return the value.
+     */
+    public synchronized String getValue(String name) {
+        if (map == null) {
+            return null;
+        }
+        return (String)map.get(name);
+    }
+
+    /**
+     * Sets a value given the name.
+     *
+     * @param name the name.
+     * @param value the value.
+     */
+    public synchronized void setValue(String name, String value) {
+        if (map == null) {
+            map = new HashMap<String,String>();
+        }
+        map.put(name, value);
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/packet/DelayInfo.java b/src/org/jivesoftware/smackx/packet/DelayInfo.java
new file mode 100644
index 0000000..f404971
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DelayInfo.java
@@ -0,0 +1,105 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import java.util.Date;
+
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * A decorator for the {@link DelayInformation} class to transparently support
+ * both the new <b>Delay Delivery</b> specification <a href="http://xmpp.org/extensions/xep-0203.html">XEP-0203</a> and 
+ * the old one <a href="http://xmpp.org/extensions/xep-0091.html">XEP-0091</a>.
+ * 
+ * Existing code can be backward compatible. 
+ * 
+ * @author Robin Collier
+ */
+public class DelayInfo extends DelayInformation
+{
+    
+	DelayInformation wrappedInfo;
+
+        /**
+         * Creates a new instance with given delay information. 
+         * @param delay the delay information
+         */
+	public DelayInfo(DelayInformation delay)
+	{
+		super(delay.getStamp());
+		wrappedInfo = delay;
+	}
+	
+	@Override
+	public String getFrom()
+	{
+		return wrappedInfo.getFrom();
+	}
+
+	@Override
+	public String getReason()
+	{
+		return wrappedInfo.getReason();
+	}
+
+	@Override
+	public Date getStamp()
+	{
+		return wrappedInfo.getStamp();
+	}
+
+	@Override
+	public void setFrom(String from)
+	{
+		wrappedInfo.setFrom(from);
+	}
+
+	@Override
+	public void setReason(String reason)
+	{
+		wrappedInfo.setReason(reason);
+	}
+
+	@Override
+	public String getElementName()
+	{
+		return "delay";
+	}
+
+	@Override
+	public String getNamespace()
+	{
+		return "urn:xmpp:delay";
+	}
+
+	@Override
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+                "\"");
+        buf.append(" stamp=\"");
+        buf.append(StringUtils.formatXEP0082Date(getStamp()));
+        buf.append("\"");
+        if (getFrom() != null && getFrom().length() > 0) {
+            buf.append(" from=\"").append(getFrom()).append("\"");
+        }
+        buf.append(">");
+        if (getReason() != null && getReason().length() > 0) {
+            buf.append(getReason());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+	
+}
diff --git a/src/org/jivesoftware/smackx/packet/DelayInformation.java b/src/org/jivesoftware/smackx/packet/DelayInformation.java
new file mode 100644
index 0000000..b9ab485
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DelayInformation.java
@@ -0,0 +1,149 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.TimeZone;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents timestamp information about data stored for later delivery. A DelayInformation will 
+ * always includes the timestamp when the packet was originally sent and may include more 
+ * information such as the JID of the entity that originally sent the packet as well as the reason
+ * for the delay.<p>
+ * 
+ * For more information see <a href="http://xmpp.org/extensions/xep-0091.html">XEP-0091</a>
+ * and <a href="http://xmpp.org/extensions/xep-0203.html">XEP-0203</a>.
+ * 
+ * @author Gaston Dombiak
+ */
+public class DelayInformation implements PacketExtension {
+
+    /**
+     * Date format according to the obsolete XEP-0091 specification.
+     * XEP-0091 recommends to use this old format for date-time instead of
+     * the one specified in XEP-0082.
+     * <p>
+     * Date formats are not synchronized. Since multiple threads access the format concurrently,
+     * it must be synchronized externally. 
+     */
+    public static final DateFormat XEP_0091_UTC_FORMAT = new SimpleDateFormat(
+            "yyyyMMdd'T'HH:mm:ss");
+    static {
+        XEP_0091_UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("UTC"));
+    }
+
+    private Date stamp;
+    private String from;
+    private String reason;
+
+    /**
+     * Creates a new instance with the specified timestamp. 
+     * @param stamp the timestamp
+     */
+    public DelayInformation(Date stamp) {
+        super();
+        this.stamp = stamp;
+    }
+
+    /**
+     * Returns the JID of the entity that originally sent the packet or that delayed the 
+     * delivery of the packet or <tt>null</tt> if this information is not available.
+     * 
+     * @return the JID of the entity that originally sent the packet or that delayed the 
+     *         delivery of the packet.
+     */
+    public String getFrom() {
+        return from;
+    }
+
+    /**
+     * Sets the JID of the entity that originally sent the packet or that delayed the 
+     * delivery of the packet or <tt>null</tt> if this information is not available.
+     * 
+     * @param from the JID of the entity that originally sent the packet.
+     */
+    public void setFrom(String from) {
+        this.from = from;
+    }
+
+    /**
+     * Returns the timestamp when the packet was originally sent. The returned Date is 
+     * be understood as UTC.
+     * 
+     * @return the timestamp when the packet was originally sent.
+     */
+    public Date getStamp() {
+        return stamp;
+    }
+
+    /**
+     * Returns a natural-language description of the reason for the delay or <tt>null</tt> if 
+     * this information is not available.
+     * 
+     * @return a natural-language description of the reason for the delay or <tt>null</tt>.
+     */
+    public String getReason() {
+        return reason;
+    }
+
+    /**
+     * Sets a natural-language description of the reason for the delay or <tt>null</tt> if 
+     * this information is not available.
+     * 
+     * @param reason a natural-language description of the reason for the delay or <tt>null</tt>.
+     */
+    public void setReason(String reason) {
+        this.reason = reason;
+    }
+
+    public String getElementName() {
+        return "x";
+    }
+
+    public String getNamespace() {
+        return "jabber:x:delay";
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+                "\"");
+        buf.append(" stamp=\"");
+        synchronized (XEP_0091_UTC_FORMAT) {
+            buf.append(XEP_0091_UTC_FORMAT.format(stamp));
+        }
+        buf.append("\"");
+        if (from != null && from.length() > 0) {
+            buf.append(" from=\"").append(from).append("\"");
+        }
+        buf.append(">");
+        if (reason != null && reason.length() > 0) {
+            buf.append(reason);
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/DiscoverInfo.java b/src/org/jivesoftware/smackx/packet/DiscoverInfo.java
new file mode 100644
index 0000000..ba873a9
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DiscoverInfo.java
@@ -0,0 +1,507 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+/**
+ * A DiscoverInfo IQ packet, which is used by XMPP clients to request and receive information 
+ * to/from other XMPP entities.<p> 
+ * 
+ * The received information may contain one or more identities of the requested XMPP entity, and 
+ * a list of supported features by the requested XMPP entity.
+ *
+ * @author Gaston Dombiak
+ */
+public class DiscoverInfo extends IQ {
+
+    public static final String NAMESPACE = "http://jabber.org/protocol/disco#info";
+
+    private final List<Feature> features = new CopyOnWriteArrayList<Feature>();
+    private final List<Identity> identities = new CopyOnWriteArrayList<Identity>();
+    private String node;
+
+    public DiscoverInfo() {
+        super();
+    }
+
+    /**
+     * Copy constructor
+     * 
+     * @param d
+     */
+    public DiscoverInfo(DiscoverInfo d) {
+        super(d);
+
+        // Set node
+        setNode(d.getNode());
+
+        // Copy features
+        synchronized (d.features) {
+            for (Feature f : d.features) {
+                addFeature(f);
+            }
+        }
+
+        // Copy identities
+        synchronized (d.identities) {
+            for (Identity i : d.identities) {
+                addIdentity(i);
+            }
+        }
+    }
+
+    /**
+     * Adds a new feature to the discovered information.
+     *
+     * @param feature the discovered feature
+     */
+    public void addFeature(String feature) {
+        addFeature(new Feature(feature));
+    }
+
+    /**
+     * Adds a collection of features to the packet. Does noting if featuresToAdd is null.
+     *
+     * @param featuresToAdd
+     */
+    public void addFeatures(Collection<String> featuresToAdd) {
+        if (featuresToAdd == null) return;
+        for (String feature : featuresToAdd) {
+            addFeature(feature);
+        }
+    }
+
+    private void addFeature(Feature feature) {
+        synchronized (features) {
+            features.add(feature);
+        }
+    }
+
+    /**
+     * Returns the discovered features of an XMPP entity.
+     *
+     * @return an Iterator on the discovered features of an XMPP entity
+     */
+    public Iterator<Feature> getFeatures() {
+        synchronized (features) {
+            return Collections.unmodifiableList(features).iterator();
+        }
+    }
+
+    /**
+     * Adds a new identity of the requested entity to the discovered information.
+     * 
+     * @param identity the discovered entity's identity
+     */
+    public void addIdentity(Identity identity) {
+        synchronized (identities) {
+            identities.add(identity);
+        }
+    }
+
+    /**
+     * Adds identities to the DiscoverInfo stanza
+     * 
+     * @param identitiesToAdd
+     */
+    public void addIdentities(Collection<Identity> identitiesToAdd) {
+        if (identitiesToAdd == null) return;
+        synchronized (identities) {
+            identities.addAll(identitiesToAdd);
+        }
+    }
+
+    /**
+     * Returns the discovered identities of an XMPP entity.
+     * 
+     * @return an Iterator on the discoveted identities 
+     */
+    public Iterator<Identity> getIdentities() {
+        synchronized (identities) {
+            return Collections.unmodifiableList(identities).iterator();
+        }
+    }
+
+    /**
+     * Returns the node attribute that supplements the 'jid' attribute. A node is merely 
+     * something that is associated with a JID and for which the JID can provide information.<p> 
+     * 
+     * Node attributes SHOULD be used only when trying to provide or query information which 
+     * is not directly addressable.
+     *
+     * @return the node attribute that supplements the 'jid' attribute
+     */
+    public String getNode() {
+        return node;
+    }
+
+    /**
+     * Sets the node attribute that supplements the 'jid' attribute. A node is merely 
+     * something that is associated with a JID and for which the JID can provide information.<p> 
+     * 
+     * Node attributes SHOULD be used only when trying to provide or query information which 
+     * is not directly addressable.
+     * 
+     * @param node the node attribute that supplements the 'jid' attribute
+     */
+    public void setNode(String node) {
+        this.node = node;
+    }
+
+    /**
+     * Returns true if the specified feature is part of the discovered information.
+     * 
+     * @param feature the feature to check
+     * @return true if the requestes feature has been discovered
+     */
+    public boolean containsFeature(String feature) {
+        for (Iterator<Feature> it = getFeatures(); it.hasNext();) {
+            if (feature.equals(it.next().getVar()))
+                return true;
+        }
+        return false;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"" + NAMESPACE + "\"");
+        if (getNode() != null) {
+            buf.append(" node=\"");
+            buf.append(StringUtils.escapeForXML(getNode()));
+            buf.append("\"");
+        }
+        buf.append(">");
+        synchronized (identities) {
+            for (Identity identity : identities) {
+                buf.append(identity.toXML());
+            }
+        }
+        synchronized (features) {
+            for (Feature feature : features) {
+                buf.append(feature.toXML());
+            }
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * Test if a DiscoverInfo response contains duplicate identities.
+     * 
+     * @return true if duplicate identities where found, otherwise false
+     */
+    public boolean containsDuplicateIdentities() {
+        List<Identity> checkedIdentities = new LinkedList<Identity>();
+        for (Identity i : identities) {
+            for (Identity i2 : checkedIdentities) {
+                if (i.equals(i2))
+                    return true;
+            }
+            checkedIdentities.add(i);
+        }
+        return false;
+    }
+
+    /**
+     * Test if a DiscoverInfo response contains duplicate features.
+     * 
+     * @return true if duplicate identities where found, otherwise false
+     */
+    public boolean containsDuplicateFeatures() {
+        List<Feature> checkedFeatures = new LinkedList<Feature>();
+        for (Feature f : features) {
+            for (Feature f2 : checkedFeatures) {
+                if (f.equals(f2))
+                    return true;
+            }
+            checkedFeatures.add(f);
+        }
+        return false;
+    }
+
+    /**
+     * Represents the identity of a given XMPP entity. An entity may have many identities but all
+     * the identities SHOULD have the same name.<p>
+     * 
+     * Refer to <a href="http://www.jabber.org/registrar/disco-categories.html">Jabber::Registrar</a>
+     * in order to get the official registry of values for the <i>category</i> and <i>type</i> 
+     * attributes.
+     * 
+     */
+    public static class Identity implements Comparable<Identity> {
+
+        private String category;
+        private String name;
+        private String type;
+        private String lang; // 'xml:lang;
+
+        /**
+         * Creates a new identity for an XMPP entity.
+         * 
+         * @param category the entity's category.
+         * @param name the entity's name.
+         * @deprecated As per the spec, the type field is mandatory and the 3 argument constructor should be used instead.
+         */
+        public Identity(String category, String name) {
+            this.category = category;
+            this.name = name;
+        }
+        
+        /**
+         * Creates a new identity for an XMPP entity.
+         * 'category' and 'type' are required by 
+         * <a href="http://xmpp.org/extensions/xep-0030.html#schemas">XEP-30 XML Schemas</a>
+         * 
+         * @param category the entity's category (required as per XEP-30).
+         * @param name the entity's name.
+         * @param type the entity's type (required as per XEP-30).
+         */
+        public Identity(String category, String name, String type) {
+            if ((category == null) || (type == null))
+                throw new IllegalArgumentException("category and type cannot be null");
+            
+            this.category = category;
+            this.name = name;
+            this.type = type;
+        }
+
+        /**
+         * Returns the entity's category. To get the official registry of values for the 
+         * 'category' attribute refer to <a href="http://www.jabber.org/registrar/disco-categories.html">Jabber::Registrar</a> 
+         *
+         * @return the entity's category.
+         */
+        public String getCategory() {
+            return category;
+        }
+
+        /**
+         * Returns the identity's name.
+         *
+         * @return the identity's name.
+         */
+        public String getName() {
+            return name;
+        }
+
+        /**
+         * Returns the entity's type. To get the official registry of values for the 
+         * 'type' attribute refer to <a href="http://www.jabber.org/registrar/disco-categories.html">Jabber::Registrar</a> 
+         *
+         * @return the entity's type.
+         */
+        public String getType() {
+            return type;
+        }
+
+        /**
+         * Sets the entity's type. To get the official registry of values for the 
+         * 'type' attribute refer to <a href="http://www.jabber.org/registrar/disco-categories.html">Jabber::Registrar</a> 
+         *
+         * @param type the identity's type.
+         * @deprecated As per the spec, this field is mandatory and the 3 argument constructor should be used instead.
+         */
+        public void setType(String type) {
+            this.type = type;
+        }
+
+        /**
+         * Sets the natural language (xml:lang) for this identity (optional)
+         * 
+         * @param lang the xml:lang of this Identity
+         */
+        public void setLanguage(String lang) {
+            this.lang = lang;
+        }
+
+        /**
+         * Returns the identities natural language if one is set
+         * 
+         * @return the value of xml:lang of this Identity
+         */
+        public String getLanguage() {
+            return lang;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<identity");
+            // Check if this packet has 'lang' set and maybe append it to the resulting string
+            if (lang != null)
+                buf.append(" xml:lang=\"").append(StringUtils.escapeForXML(lang)).append("\"");
+            // Category must always be set
+            buf.append(" category=\"").append(StringUtils.escapeForXML(category)).append("\"");
+            // Name must always be set
+            buf.append(" name=\"").append(StringUtils.escapeForXML(name)).append("\"");
+            // Check if this packet has 'type' set and maybe append it to the resulting string
+            if (type != null) {
+                buf.append(" type=\"").append(StringUtils.escapeForXML(type)).append("\"");
+            }
+            buf.append("/>");
+            return buf.toString();
+        }
+
+        /** 
+         * Check equality for Identity  for category, type, lang and name
+         * in that order as defined by
+         * <a href="http://xmpp.org/extensions/xep-0115.html#ver-proc">XEP-0015 5.4 Processing Method (Step 3.3)</a>
+         *  
+         */
+        public boolean equals(Object obj) {
+            if (obj == null)
+                return false;
+            if (obj == this)
+                return true;
+            if (obj.getClass() != getClass())
+                return false;
+
+            DiscoverInfo.Identity other = (DiscoverInfo.Identity) obj;
+            if (!this.category.equals(other.category))
+                return false;
+
+            String otherLang = other.lang == null ? "" : other.lang;
+            String thisLang = lang == null ? "" : lang;
+            if (!otherLang.equals(thisLang))
+                return false;
+            
+            // This safeguard can be removed once the deprecated constructor is removed.
+            String otherType = other.type == null ? "" : other.type;
+            String thisType = type == null ? "" : type;
+            if (!otherType.equals(thisType))
+                return false;
+
+            String otherName = other.name == null ? "" : other.name;
+            String thisName = name == null ? "" : other.name;
+            if (!thisName.equals(otherName))
+                return false;
+
+            return true;
+        }
+        
+        @Override
+        public int hashCode() {
+            int result = 1;
+            result = 37 * result + category.hashCode();
+            result = 37 * result + (lang == null ? 0 : lang.hashCode());
+            result = 37 * result + (type == null ? 0 : type.hashCode());
+            result = 37 * result + (name == null ? 0 : name.hashCode());
+            return result;
+        }
+
+        /**
+         * Compares this identity with another one. The comparison order is:
+         * Category, Type, Lang. If all three are identical the other Identity is considered equal.
+         * Name is not used for comparision, as defined by XEP-0115
+         * 
+         * @param obj
+         * @return
+         */
+        public int compareTo(DiscoverInfo.Identity other) {
+            String otherLang = other.lang == null ? "" : other.lang;
+            String thisLang = lang == null ? "" : lang;
+            
+            // This can be removed once the deprecated constructor is removed.
+            String otherType = other.type == null ? "" : other.type;
+            String thisType = type == null ? "" : type;
+
+            if (category.equals(other.category)) {
+                if (thisType.equals(otherType)) {
+                    if (thisLang.equals(otherLang)) {
+                        // Don't compare on name, XEP-30 says that name SHOULD
+                        // be equals for all identities of an entity
+                        return 0;
+                    } else {
+                        return thisLang.compareTo(otherLang);
+                    }
+                } else {
+                    return thisType.compareTo(otherType);
+                }
+            } else {
+                return category.compareTo(other.category);
+            }
+        }
+    }
+
+    /**
+     * Represents the features offered by the item. This information helps requestors determine 
+     * what actions are possible with regard to this item (registration, search, join, etc.) 
+     * as well as specific feature types of interest, if any (e.g., for the purpose of feature 
+     * negotiation).
+     */
+    public static class Feature {
+
+        private String variable;
+
+        /**
+         * Creates a new feature offered by an XMPP entity or item.
+         * 
+         * @param variable the feature's variable.
+         */
+        public Feature(String variable) {
+            if (variable == null)
+                throw new IllegalArgumentException("variable cannot be null");
+            this.variable = variable;
+        }
+
+        /**
+         * Returns the feature's variable.
+         *
+         * @return the feature's variable.
+         */
+        public String getVar() {
+            return variable;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<feature var=\"").append(StringUtils.escapeForXML(variable)).append("\"/>");
+            return buf.toString();
+        }
+
+        public boolean equals(Object obj) {
+            if (obj == null)
+                return false;
+            if (obj == this)
+                return true;
+            if (obj.getClass() != getClass())
+                return false;
+
+            DiscoverInfo.Feature other = (DiscoverInfo.Feature) obj;
+            return variable.equals(other.variable);
+        }
+
+        @Override
+        public int hashCode() {
+            return 37 * variable.hashCode();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/DiscoverItems.java b/src/org/jivesoftware/smackx/packet/DiscoverItems.java
new file mode 100644
index 0000000..f6a0941
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/DiscoverItems.java
@@ -0,0 +1,253 @@
+/**
+ * $RCSfile$
+ * $Revision: 7071 $
+ * $Date: 2007-02-12 08:59:05 +0800 (Mon, 12 Feb 2007) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+/**
+ * A DiscoverItems IQ packet, which is used by XMPP clients to request and receive items 
+ * associated with XMPP entities.<p>
+ * 
+ * The items could also be queried in order to discover if they contain items inside. Some items 
+ * may be addressable by its JID and others may require to be addressed by a JID and a node name.
+ *
+ * @author Gaston Dombiak
+ */
+public class DiscoverItems extends IQ {
+
+    public static final String NAMESPACE = "http://jabber.org/protocol/disco#items";
+
+    private final List<Item> items = new CopyOnWriteArrayList<Item>();
+    private String node;
+
+    /**
+     * Adds a new item to the discovered information.
+     * 
+     * @param item the discovered entity's item
+     */
+    public void addItem(Item item) {
+        synchronized (items) {
+            items.add(item);
+        }
+    }
+
+    /**
+     * Adds a collection of items to the discovered information. Does nothing if itemsToAdd is null
+     *
+     * @param itemsToAdd
+     */
+    public void addItems(Collection<Item> itemsToAdd) {
+        if (itemsToAdd == null) return;
+        for (Item i : itemsToAdd) {
+            addItem(i);
+        }
+    }
+
+    /**
+     * Returns the discovered items of the queried XMPP entity. 
+     *
+     * @return an Iterator on the discovered entity's items
+     */
+    public Iterator<DiscoverItems.Item> getItems() {
+        synchronized (items) {
+            return Collections.unmodifiableList(items).iterator();
+        }
+    }
+
+    /**
+     * Returns the node attribute that supplements the 'jid' attribute. A node is merely 
+     * something that is associated with a JID and for which the JID can provide information.<p> 
+     * 
+     * Node attributes SHOULD be used only when trying to provide or query information which 
+     * is not directly addressable.
+     *
+     * @return the node attribute that supplements the 'jid' attribute
+     */
+    public String getNode() {
+        return node;
+    }
+
+    /**
+     * Sets the node attribute that supplements the 'jid' attribute. A node is merely 
+     * something that is associated with a JID and for which the JID can provide information.<p> 
+     * 
+     * Node attributes SHOULD be used only when trying to provide or query information which 
+     * is not directly addressable.
+     * 
+     * @param node the node attribute that supplements the 'jid' attribute
+     */
+    public void setNode(String node) {
+        this.node = node;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"" + NAMESPACE + "\"");
+        if (getNode() != null) {
+            buf.append(" node=\"");
+            buf.append(StringUtils.escapeForXML(getNode()));
+            buf.append("\"");
+        }
+        buf.append(">");
+        synchronized (items) {
+            for (Item item : items) {
+                buf.append(item.toXML());
+            }
+        }
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * An item is associated with an XMPP Entity, usually thought of a children of the parent 
+     * entity and normally are addressable as a JID.<p> 
+     * 
+     * An item associated with an entity may not be addressable as a JID. In order to handle 
+     * such items, Service Discovery uses an optional 'node' attribute that supplements the 
+     * 'jid' attribute.
+     */
+    public static class Item {
+
+        /**
+         * Request to create or update the item.
+         */
+        public static final String UPDATE_ACTION = "update";
+
+        /**
+         * Request to remove the item.
+         */
+        public static final String REMOVE_ACTION = "remove";
+
+        private String entityID;
+        private String name;
+        private String node;
+        private String action;
+
+        /**
+         * Create a new Item associated with a given entity.
+         * 
+         * @param entityID the id of the entity that contains the item
+         */
+        public Item(String entityID) {
+            this.entityID = entityID;
+        }
+
+        /**
+         * Returns the entity's ID.
+         *
+         * @return the entity's ID.
+         */
+        public String getEntityID() {
+            return entityID;
+        }
+
+        /**
+         * Returns the entity's name.
+         *
+         * @return the entity's name.
+         */
+        public String getName() {
+            return name;
+        }
+
+        /**
+         * Sets the entity's name.
+         *
+         * @param name the entity's name.
+         */
+        public void setName(String name) {
+            this.name = name;
+        }
+
+        /**
+         * Returns the node attribute that supplements the 'jid' attribute. A node is merely 
+         * something that is associated with a JID and for which the JID can provide information.<p> 
+         * 
+         * Node attributes SHOULD be used only when trying to provide or query information which 
+         * is not directly addressable.
+         *
+         * @return the node attribute that supplements the 'jid' attribute
+         */
+        public String getNode() {
+            return node;
+        }
+
+        /**
+         * Sets the node attribute that supplements the 'jid' attribute. A node is merely 
+         * something that is associated with a JID and for which the JID can provide information.<p> 
+         * 
+         * Node attributes SHOULD be used only when trying to provide or query information which 
+         * is not directly addressable.
+         * 
+         * @param node the node attribute that supplements the 'jid' attribute
+         */
+        public void setNode(String node) {
+            this.node = node;
+        }
+
+        /**
+         * Returns the action that specifies the action being taken for this item. Possible action 
+         * values are: "update" and "remove". Update should either create a new entry if the node 
+         * and jid combination does not already exist, or simply update an existing entry. If 
+         * "remove" is used as the action, the item should be removed from persistent storage.
+         *  
+         * @return the action being taken for this item
+         */
+        public String getAction() {
+            return action;
+        }
+
+        /**
+         * Sets the action that specifies the action being taken for this item. Possible action 
+         * values are: "update" and "remove". Update should either create a new entry if the node 
+         * and jid combination does not already exist, or simply update an existing entry. If 
+         * "remove" is used as the action, the item should be removed from persistent storage.
+         * 
+         * @param action the action being taken for this item
+         */
+        public void setAction(String action) {
+            this.action = action;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item jid=\"").append(entityID).append("\"");
+            if (name != null) {
+                buf.append(" name=\"").append(StringUtils.escapeForXML(name)).append("\"");
+            }
+            if (node != null) {
+                buf.append(" node=\"").append(StringUtils.escapeForXML(node)).append("\"");
+            }
+            if (action != null) {
+                buf.append(" action=\"").append(StringUtils.escapeForXML(action)).append("\"");
+            }
+            buf.append("/>");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/Header.java b/src/org/jivesoftware/smackx/packet/Header.java
new file mode 100644
index 0000000..3fa8386
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/Header.java
@@ -0,0 +1,59 @@
+/*
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents a <b>Header</b> entry as specified by the <a href="http://xmpp.org/extensions/xep-031.html">Stanza Headers and Internet Metadata (SHIM)</a>
+
+ * @author Robin Collier
+ */
+public class Header implements PacketExtension
+{
+	private String name;
+	private String value;
+	
+	public Header(String name, String value)
+	{
+		this.name = name;
+		this.value = value;
+	}
+	
+	public String getName()
+	{
+		return name;
+	}
+
+	public String getValue()
+	{
+		return value;
+	}
+
+	public String getElementName()
+	{
+		return "header";
+	}
+
+	public String getNamespace()
+	{
+		return HeadersExtension.NAMESPACE;
+	}
+
+	public String toXML()
+	{
+		return "<header name='" + name + "'>" + value + "</header>";
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/HeadersExtension.java b/src/org/jivesoftware/smackx/packet/HeadersExtension.java
new file mode 100644
index 0000000..78564db
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/HeadersExtension.java
@@ -0,0 +1,69 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import java.util.Collection;
+import java.util.Collections;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Extension representing a list of headers as specified in <a href="http://xmpp.org/extensions/xep-0131">Stanza Headers and Internet Metadata (SHIM)</a>
+ * 
+ * @see Header
+ * 
+ * @author Robin Collier
+ */
+public class HeadersExtension implements PacketExtension
+{
+	public static final String NAMESPACE = "http://jabber.org/protocol/shim";
+	
+	private Collection<Header> headers = Collections.EMPTY_LIST;
+	
+	public HeadersExtension(Collection<Header> headerList)
+	{
+		if (headerList != null)
+			headers = headerList;
+	}
+	
+	public Collection<Header> getHeaders()
+	{
+		return headers;
+	}
+
+	public String getElementName()
+	{
+		return "headers";
+	}
+
+	public String getNamespace()
+	{
+		return NAMESPACE;
+	}
+
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<" + getElementName() + " xmlns='" + getNamespace() + "'>");
+		
+		for (Header header : headers)
+		{
+			builder.append(header.toXML());
+		}
+		builder.append("</" + getElementName() + '>');
+
+		return builder.toString();
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/LastActivity.java b/src/org/jivesoftware/smackx/packet/LastActivity.java
new file mode 100644
index 0000000..6f4f15a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/LastActivity.java
@@ -0,0 +1,164 @@
+/**
+ * $RCSfile$
+ * $Revision: 2407 $
+ * $Date: 2004-11-02 15:37:00 -0800 (Tue, 02 Nov 2004) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import java.io.IOException;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+/**
+ * A last activity IQ for retrieving information about the last activity associated with a Jabber ID.
+ * LastActivity (XEP-0012) allows for retrieval of how long a particular user has been idle and the
+ * message the specified when doing so. Use {@link org.jivesoftware.smackx.LastActivityManager}
+ * to get the last activity of a user.
+ *
+ * @author Derek DeMoro
+ */
+public class LastActivity extends IQ {
+
+    public static final String NAMESPACE = "jabber:iq:last";
+
+    public long lastActivity = -1;
+    public String message;
+
+    public LastActivity() {
+        setType(IQ.Type.GET);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"" + NAMESPACE + "\"");
+        if (lastActivity != -1) {
+            buf.append(" seconds=\"").append(lastActivity).append("\"");
+        }
+        buf.append("></query>");
+        return buf.toString();
+    }
+
+
+    public void setLastActivity(long lastActivity) {
+        this.lastActivity = lastActivity;
+    }
+
+
+    private void setMessage(String message) {
+        this.message = message;
+    }
+
+    /**
+     * Returns number of seconds that have passed since the user last logged out.
+     * If the user is offline, 0 will be returned.
+     *
+     * @return the number of seconds that have passed since the user last logged out.
+     */
+    public long getIdleTime() {
+        return lastActivity;
+    }
+
+
+    /**
+     * Returns the status message of the last unavailable presence received from the user.
+     *
+     * @return the status message of the last unavailable presence received from the user
+     */
+    public String getStatusMessage() {
+        return message;
+    }
+
+
+    /**
+     * The IQ Provider for LastActivity.
+     *
+     * @author Derek DeMoro
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws XMPPException, XmlPullParserException {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new XMPPException("Parser not in proper position, or bad XML.");
+            }
+
+            LastActivity lastActivity = new LastActivity();
+            String seconds = parser.getAttributeValue("", "seconds");
+            String message = null;
+            try {
+                message = parser.nextText();
+            } catch (IOException e1) {
+                // Ignore
+            }
+            if (seconds != null) {
+                try {
+                    lastActivity.setLastActivity(Long.parseLong(seconds));
+                } catch (NumberFormatException e) {
+                    // Ignore
+                }
+            }
+
+            if (message != null) {
+                lastActivity.setMessage(message);
+            }
+            return lastActivity;
+        }
+    }
+
+    /**
+     * Retrieve the last activity of a particular jid.
+     * @param con the current Connection.
+     * @param jid the JID of the user.
+     * @return the LastActivity packet of the jid.
+     * @throws XMPPException thrown if a server error has occured.
+     * @deprecated This method only retreives the lapsed time since the last logout of a particular jid. 
+     * Replaced by {@link  org.jivesoftware.smackx.LastActivityManager#getLastActivity(Connection, String)  getLastActivity}
+     */
+    public static LastActivity getLastActivity(Connection con, String jid) throws XMPPException {
+        LastActivity activity = new LastActivity();
+        jid = StringUtils.parseBareAddress(jid);
+        activity.setTo(jid);
+
+        PacketCollector collector = con.createPacketCollector(new PacketIDFilter(activity.getPacketID()));
+        con.sendPacket(activity);
+
+        LastActivity response = (LastActivity) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/MUCAdmin.java b/src/org/jivesoftware/smackx/packet/MUCAdmin.java
new file mode 100644
index 0000000..75d17e0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MUCAdmin.java
@@ -0,0 +1,237 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+import org.jivesoftware.smack.packet.IQ;
+
+/**
+ * IQ packet that serves for kicking users, granting and revoking voice, banning users, 
+ * modifying the ban list, granting and revoking membership and granting and revoking 
+ * moderator privileges. All these operations are scoped by the 
+ * 'http://jabber.org/protocol/muc#admin' namespace.
+ * 
+ * @author Gaston Dombiak
+ */
+public class MUCAdmin extends IQ {
+
+    private List<Item> items = new ArrayList<Item>();
+
+    /**
+     * Returns an Iterator for item childs that holds information about roles, affiliation, 
+     * jids and nicks.
+     * 
+     * @return an Iterator for item childs that holds information about roles, affiliation,
+     *          jids and nicks.
+     */
+    public Iterator<Item> getItems() {
+        synchronized (items) {
+            return Collections.unmodifiableList(new ArrayList<Item>(items)).iterator();
+        }
+    }
+
+    /**
+     * Adds an item child that holds information about roles, affiliation, jids and nicks.
+     * 
+     * @param item the item child that holds information about roles, affiliation, jids and nicks.
+     */
+    public void addItem(Item item) {
+        synchronized (items) {
+            items.add(item);
+        }
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"http://jabber.org/protocol/muc#admin\">");
+        synchronized (items) {
+            for (int i = 0; i < items.size(); i++) {
+                Item item = items.get(i);
+                buf.append(item.toXML());
+            }
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * Item child that holds information about roles, affiliation, jids and nicks.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Item {
+        private String actor;
+        private String reason;
+        private String affiliation;
+        private String jid;
+        private String nick;
+        private String role;
+        
+        /**
+         * Creates a new item child. 
+         * 
+         * @param affiliation the actor's affiliation to the room
+         * @param role the privilege level of an occupant within a room.
+         */
+        public Item(String affiliation, String role) {
+            this.affiliation = affiliation;
+            this.role = role;
+        }
+        
+        /**
+         * Returns the actor (JID of an occupant in the room) that was kicked or banned.
+         * 
+         * @return the JID of an occupant in the room that was kicked or banned.
+         */
+        public String getActor() {
+            return actor;
+        }
+
+        /**
+         * Returns the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         *  
+         * @return the reason for the item child.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Returns the occupant's affiliation to the room. The affiliation is a semi-permanent 
+         * association or connection with a room. The possible affiliations are "owner", "admin", 
+         * "member", and "outcast" (naturally it is also possible to have no affiliation). An 
+         * affiliation lasts across a user's visits to a room.
+         * 
+         * @return the actor's affiliation to the room
+         */
+        public String getAffiliation() {
+            return affiliation;
+        }
+
+        /**
+         * Returns the <room@service/nick> by which an occupant is identified within the context 
+         * of a room. If the room is non-anonymous, the JID will be included in the item. 
+         * 
+         * @return the room JID by which an occupant is identified within the room.
+         */
+        public String getJid() {
+            return jid;
+        }
+
+        /**
+         * Returns the new nickname of an occupant that is changing his/her nickname. The new 
+         * nickname is sent as part of the unavailable presence.  
+         * 
+         * @return the new nickname of an occupant that is changing his/her nickname.
+         */
+        public String getNick() {
+            return nick;
+        }
+
+        /**
+         * Returns the temporary position or privilege level of an occupant within a room. The 
+         * possible roles are "moderator", "participant", and "visitor" (it is also possible to 
+         * have no defined role). A role lasts only for the duration of an occupant's visit to 
+         * a room. 
+         * 
+         * @return the privilege level of an occupant within a room.
+         */
+        public String getRole() {
+            return role;
+        }
+
+        /**
+         * Sets the actor (JID of an occupant in the room) that was kicked or banned.
+         * 
+         * @param actor the actor (JID of an occupant in the room) that was kicked or banned.
+         */
+        public void setActor(String actor) {
+            this.actor = actor;
+        }
+
+        /**
+         * Sets the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         * 
+         * @param reason the reason why a user (occupant) was kicked or banned.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        /**
+         * Sets the <room@service/nick> by which an occupant is identified within the context 
+         * of a room. If the room is non-anonymous, the JID will be included in the item.
+         *  
+         * @param jid the JID by which an occupant is identified within a room.
+         */
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        /**
+         * Sets the new nickname of an occupant that is changing his/her nickname. The new 
+         * nickname is sent as part of the unavailable presence.
+         *   
+         * @param nick the new nickname of an occupant that is changing his/her nickname.
+         */
+        public void setNick(String nick) {
+            this.nick = nick;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item");
+            if (getAffiliation() != null) {
+                buf.append(" affiliation=\"").append(getAffiliation()).append("\"");
+            }
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getNick() != null) {
+                buf.append(" nick=\"").append(getNick()).append("\"");
+            }
+            if (getRole() != null) {
+                buf.append(" role=\"").append(getRole()).append("\"");
+            }
+            if (getReason() == null && getActor() == null) {
+                buf.append("/>");
+            }
+            else {
+                buf.append(">");
+                if (getReason() != null) {
+                    buf.append("<reason>").append(getReason()).append("</reason>");
+                }
+                if (getActor() != null) {
+                    buf.append("<actor jid=\"").append(getActor()).append("\"/>");
+                }
+                buf.append("</item>");
+            }
+            return buf.toString();
+        }
+    };
+}
diff --git a/src/org/jivesoftware/smackx/packet/MUCInitialPresence.java b/src/org/jivesoftware/smackx/packet/MUCInitialPresence.java
new file mode 100644
index 0000000..d3d2796
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MUCInitialPresence.java
@@ -0,0 +1,223 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.TimeZone;
+
+/**
+ * Represents extended presence information whose sole purpose is to signal the ability of 
+ * the occupant to speak the MUC protocol when joining a room. If the room requires a password 
+ * then the MUCInitialPresence should include one.<p>
+ * 
+ * The amount of discussion history provided on entering a room (perhaps because the 
+ * user is on a low-bandwidth connection or is using a small-footprint client) could be managed by
+ * setting a configured History instance to the MUCInitialPresence instance. 
+ * @see MUCInitialPresence#setHistory(MUCInitialPresence.History).
+ *
+ * @author Gaston Dombiak
+ */
+public class MUCInitialPresence implements PacketExtension {
+
+    private String password;
+    private History history; 
+
+    public String getElementName() {
+        return "x";
+    }
+
+    public String getNamespace() {
+        return "http://jabber.org/protocol/muc";
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        if (getPassword() != null) {
+            buf.append("<password>").append(getPassword()).append("</password>");
+        }
+        if (getHistory() != null) {
+            buf.append(getHistory().toXML());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Returns the history that manages the amount of discussion history provided on 
+     * entering a room.
+     * 
+     * @return the history that manages the amount of discussion history provided on 
+     * entering a room.
+     */
+    public History getHistory() {
+        return history;
+    }
+
+    /**
+     * Returns the password to use when the room requires a password.
+     * 
+     * @return the password to use when the room requires a password.
+     */
+    public String getPassword() {
+        return password;
+    }
+
+    /**
+     * Sets the History that manages the amount of discussion history provided on 
+     * entering a room.
+     * 
+     * @param history that manages the amount of discussion history provided on 
+     * entering a room.
+     */
+    public void setHistory(History history) {
+        this.history = history;
+    }
+
+    /**
+     * Sets the password to use when the room requires a password.
+     * 
+     * @param password the password to use when the room requires a password.
+     */
+    public void setPassword(String password) {
+        this.password = password;
+    }
+
+    /**
+     * The History class controls the number of characters or messages to receive
+     * when entering a room.
+     * 
+     * @author Gaston Dombiak
+     */
+    public static class History {
+
+        private int maxChars = -1;
+        private int maxStanzas = -1; 
+        private int seconds = -1; 
+        private Date since; 
+
+        /**
+         * Returns the total number of characters to receive in the history.
+         * 
+         * @return total number of characters to receive in the history.
+         */
+        public int getMaxChars() {
+            return maxChars;
+        }
+
+        /**
+         * Returns the total number of messages to receive in the history.
+         * 
+         * @return the total number of messages to receive in the history.
+         */
+        public int getMaxStanzas() {
+            return maxStanzas;
+        }
+
+        /**
+         * Returns the number of seconds to use to filter the messages received during that time. 
+         * In other words, only the messages received in the last "X" seconds will be included in 
+         * the history.
+         * 
+         * @return the number of seconds to use to filter the messages received during that time.
+         */
+        public int getSeconds() {
+            return seconds;
+        }
+
+        /**
+         * Returns the since date to use to filter the messages received during that time. 
+         * In other words, only the messages received since the datetime specified will be 
+         * included in the history.
+         * 
+         * @return the since date to use to filter the messages received during that time.
+         */
+        public Date getSince() {
+            return since;
+        }
+
+        /**
+         * Sets the total number of characters to receive in the history.
+         * 
+         * @param maxChars the total number of characters to receive in the history.
+         */
+        public void setMaxChars(int maxChars) {
+            this.maxChars = maxChars;
+        }
+
+        /**
+         * Sets the total number of messages to receive in the history.
+         * 
+         * @param maxStanzas the total number of messages to receive in the history.
+         */
+        public void setMaxStanzas(int maxStanzas) {
+            this.maxStanzas = maxStanzas;
+        }
+
+        /**
+         * Sets the number of seconds to use to filter the messages received during that time. 
+         * In other words, only the messages received in the last "X" seconds will be included in 
+         * the history.
+         * 
+         * @param seconds the number of seconds to use to filter the messages received during 
+         * that time.
+         */
+        public void setSeconds(int seconds) {
+            this.seconds = seconds;
+        }
+
+        /**
+         * Sets the since date to use to filter the messages received during that time. 
+         * In other words, only the messages received since the datetime specified will be 
+         * included in the history.
+         * 
+         * @param since the since date to use to filter the messages received during that time.
+         */
+        public void setSince(Date since) {
+            this.since = since;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<history");
+            if (getMaxChars() != -1) {
+                buf.append(" maxchars=\"").append(getMaxChars()).append("\"");
+            }
+            if (getMaxStanzas() != -1) {
+                buf.append(" maxstanzas=\"").append(getMaxStanzas()).append("\"");
+            }
+            if (getSeconds() != -1) {
+                buf.append(" seconds=\"").append(getSeconds()).append("\"");
+            }
+            if (getSince() != null) {
+                SimpleDateFormat utcFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
+                utcFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
+                buf.append(" since=\"").append(utcFormat.format(getSince())).append("\"");
+            }
+            buf.append("/>");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/MUCOwner.java b/src/org/jivesoftware/smackx/packet/MUCOwner.java
new file mode 100644
index 0000000..e33806e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MUCOwner.java
@@ -0,0 +1,342 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+import org.jivesoftware.smack.packet.IQ;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * IQ packet that serves for granting and revoking ownership privileges, granting 
+ * and revoking administrative privileges and destroying a room. All these operations 
+ * are scoped by the 'http://jabber.org/protocol/muc#owner' namespace.
+ * 
+ * @author Gaston Dombiak
+ */
+public class MUCOwner extends IQ {
+
+    private List<Item> items = new ArrayList<Item>();
+    private Destroy destroy;
+
+    /**
+     * Returns an Iterator for item childs that holds information about affiliation, 
+     * jids and nicks.
+     * 
+     * @return an Iterator for item childs that holds information about affiliation,
+     *          jids and nicks.
+     */
+    public Iterator<Item> getItems() {
+        synchronized (items) {
+            return Collections.unmodifiableList(new ArrayList<Item>(items)).iterator();
+        }
+    }
+
+    /**
+     * Returns a request to the server to destroy a room. The sender of the request
+     * should be the room's owner. If the sender of the destroy request is not the room's owner
+     * then the server will answer a "Forbidden" error.
+     * 
+     * @return a request to the server to destroy a room.
+     */
+    public Destroy getDestroy() {
+        return destroy;
+    }
+
+    /**
+     * Sets a request to the server to destroy a room. The sender of the request
+     * should be the room's owner. If the sender of the destroy request is not the room's owner
+     * then the server will answer a "Forbidden" error.
+     * 
+     * @param destroy the request to the server to destroy a room.
+     */
+    public void setDestroy(Destroy destroy) {
+        this.destroy = destroy;
+    }
+
+    /**
+     * Adds an item child that holds information about affiliation, jids and nicks.
+     * 
+     * @param item the item child that holds information about affiliation, jids and nicks.
+     */
+    public void addItem(Item item) {
+        synchronized (items) {
+            items.add(item);
+        }
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"http://jabber.org/protocol/muc#owner\">");
+        synchronized (items) {
+            for (int i = 0; i < items.size(); i++) {
+                Item item = (Item) items.get(i);
+                buf.append(item.toXML());
+            }
+        }
+        if (getDestroy() != null) {
+            buf.append(getDestroy().toXML());
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * Item child that holds information about affiliation, jids and nicks.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Item {
+        
+        private String actor;
+        private String reason;
+        private String affiliation;
+        private String jid;
+        private String nick;
+        private String role;
+
+        /**
+         * Creates a new item child. 
+         * 
+         * @param affiliation the actor's affiliation to the room
+         */
+        public Item(String affiliation) {
+            this.affiliation = affiliation;
+        }
+        
+        /**
+         * Returns the actor (JID of an occupant in the room) that was kicked or banned.
+         * 
+         * @return the JID of an occupant in the room that was kicked or banned.
+         */
+        public String getActor() {
+            return actor;
+        }
+
+        /**
+         * Returns the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         *  
+         * @return the reason for the item child.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Returns the occupant's affiliation to the room. The affiliation is a semi-permanent 
+         * association or connection with a room. The possible affiliations are "owner", "admin", 
+         * "member", and "outcast" (naturally it is also possible to have no affiliation). An 
+         * affiliation lasts across a user's visits to a room.
+         * 
+         * @return the actor's affiliation to the room
+         */
+        public String getAffiliation() {
+            return affiliation;
+        }
+
+        /**
+         * Returns the <room@service/nick> by which an occupant is identified within the context 
+         * of a room. If the room is non-anonymous, the JID will be included in the item. 
+         * 
+         * @return the room JID by which an occupant is identified within the room.
+         */
+        public String getJid() {
+            return jid;
+        }
+
+        /**
+         * Returns the new nickname of an occupant that is changing his/her nickname. The new 
+         * nickname is sent as part of the unavailable presence.  
+         * 
+         * @return the new nickname of an occupant that is changing his/her nickname.
+         */
+        public String getNick() {
+            return nick;
+        }
+
+        /**
+         * Returns the temporary position or privilege level of an occupant within a room. The
+         * possible roles are "moderator", "participant", and "visitor" (it is also possible to
+         * have no defined role). A role lasts only for the duration of an occupant's visit to
+         * a room.
+         *
+         * @return the privilege level of an occupant within a room.
+         */
+        public String getRole() {
+            return role;
+        }
+
+        /**
+         * Sets the actor (JID of an occupant in the room) that was kicked or banned.
+         * 
+         * @param actor the actor (JID of an occupant in the room) that was kicked or banned.
+         */
+        public void setActor(String actor) {
+            this.actor = actor;
+        }
+
+        /**
+         * Sets the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         * 
+         * @param reason the reason why a user (occupant) was kicked or banned.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        /**
+         * Sets the <room@service/nick> by which an occupant is identified within the context 
+         * of a room. If the room is non-anonymous, the JID will be included in the item.
+         *  
+         * @param jid the JID by which an occupant is identified within a room.
+         */
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        /**
+         * Sets the new nickname of an occupant that is changing his/her nickname. The new 
+         * nickname is sent as part of the unavailable presence.
+         *   
+         * @param nick the new nickname of an occupant that is changing his/her nickname.
+         */
+        public void setNick(String nick) {
+            this.nick = nick;
+        }
+
+        /**
+         * Sets the temporary position or privilege level of an occupant within a room. The
+         * possible roles are "moderator", "participant", and "visitor" (it is also possible to
+         * have no defined role). A role lasts only for the duration of an occupant's visit to
+         * a room.
+         *
+         * @param role the new privilege level of an occupant within a room.
+         */
+        public void setRole(String role) {
+            this.role = role;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item");
+            if (getAffiliation() != null) {
+                buf.append(" affiliation=\"").append(getAffiliation()).append("\"");
+            }
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getNick() != null) {
+                buf.append(" nick=\"").append(getNick()).append("\"");
+            }
+            if (getRole() != null) {
+                buf.append(" role=\"").append(getRole()).append("\"");
+            }
+            if (getReason() == null && getActor() == null) {
+                buf.append("/>");
+            }
+            else {
+                buf.append(">");
+                if (getReason() != null) {
+                    buf.append("<reason>").append(getReason()).append("</reason>");
+                }
+                if (getActor() != null) {
+                    buf.append("<actor jid=\"").append(getActor()).append("\"/>");
+                }
+                buf.append("</item>");
+            }
+            return buf.toString();
+        }
+    };
+
+    /**
+     * Represents a request to the server to destroy a room. The sender of the request
+     * should be the room's owner. If the sender of the destroy request is not the room's owner
+     * then the server will answer a "Forbidden" error.
+     * 
+     * @author Gaston Dombiak
+     */
+    public static class Destroy {
+        private String reason;
+        private String jid;
+        
+        
+        /**
+         * Returns the JID of an alternate location since the current room is being destroyed.
+         * 
+         * @return the JID of an alternate location.
+         */
+        public String getJid() {
+            return jid;
+        }
+
+        /**
+         * Returns the reason for the room destruction.
+         * 
+         * @return the reason for the room destruction.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Sets the JID of an alternate location since the current room is being destroyed.
+         * 
+         * @param jid the JID of an alternate location.
+         */
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        /**
+         * Sets the reason for the room destruction.
+         * 
+         * @param reason the reason for the room destruction.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<destroy");
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getReason() == null) {
+                buf.append("/>");
+            }
+            else {
+                buf.append(">");
+                if (getReason() != null) {
+                    buf.append("<reason>").append(getReason()).append("</reason>");
+                }
+                buf.append("</destroy>");
+            }
+            return buf.toString();
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/MUCUser.java b/src/org/jivesoftware/smackx/packet/MUCUser.java
new file mode 100644
index 0000000..bfcd67c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MUCUser.java
@@ -0,0 +1,627 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents extended presence information about roles, affiliations, full JIDs,
+ * or status codes scoped by the 'http://jabber.org/protocol/muc#user' namespace.
+ *
+ * @author Gaston Dombiak
+ */
+public class MUCUser implements PacketExtension {
+
+    private Invite invite;
+    private Decline decline;
+    private Item item;
+    private String password;
+    private Status status;
+    private Destroy destroy;
+
+    public String getElementName() {
+        return "x";
+    }
+
+    public String getNamespace() {
+        return "http://jabber.org/protocol/muc#user";
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        if (getInvite() != null) {
+            buf.append(getInvite().toXML());
+        }
+        if (getDecline() != null) {
+            buf.append(getDecline().toXML());
+        }
+        if (getItem() != null) {
+            buf.append(getItem().toXML());
+        }
+        if (getPassword() != null) {
+            buf.append("<password>").append(getPassword()).append("</password>");
+        }
+        if (getStatus() != null) {
+            buf.append(getStatus().toXML());
+        }
+        if (getDestroy() != null) {
+            buf.append(getDestroy().toXML());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Returns the invitation for another user to a room. The sender of the invitation
+     * must be an occupant of the room. The invitation will be sent to the room which in turn
+     * will forward the invitation to the invitee.
+     *
+     * @return an invitation for another user to a room.
+     */
+    public Invite getInvite() {
+        return invite;
+    }
+
+    /**
+     * Returns the rejection to an invitation from another user to a room. The rejection will be
+     * sent to the room which in turn will forward the refusal to the inviter.
+     *
+     * @return a rejection to an invitation from another user to a room.
+     */
+    public Decline getDecline() {
+        return decline;
+    }
+
+    /**
+     * Returns the item child that holds information about roles, affiliation, jids and nicks.
+     *
+     * @return an item child that holds information about roles, affiliation, jids and nicks.
+     */
+    public Item getItem() {
+        return item;
+    }
+
+    /**
+     * Returns the password to use to enter Password-Protected Room. A Password-Protected Room is
+     * a room that a user cannot enter without first providing the correct password.
+     *
+     * @return the password to use to enter Password-Protected Room.
+     */
+    public String getPassword() {
+        return password;
+    }
+
+    /**
+     * Returns the status which holds a code that assists in presenting notification messages.
+     *
+     * @return the status which holds a code that assists in presenting notification messages.
+     */
+    public Status getStatus() {
+        return status;
+    }
+
+    /**
+     * Returns the notification that the room has been destroyed. After a room has been destroyed,
+     * the room occupants will receive a Presence packet of type 'unavailable' with the reason for
+     * the room destruction if provided by the room owner.
+     *
+     * @return a notification that the room has been destroyed.
+     */
+    public Destroy getDestroy() {
+        return destroy;
+    }
+
+    /**
+     * Sets the invitation for another user to a room. The sender of the invitation
+     * must be an occupant of the room. The invitation will be sent to the room which in turn
+     * will forward the invitation to the invitee.
+     *
+     * @param invite the invitation for another user to a room.
+     */
+    public void setInvite(Invite invite) {
+        this.invite = invite;
+    }
+
+    /**
+     * Sets the rejection to an invitation from another user to a room. The rejection will be
+     * sent to the room which in turn will forward the refusal to the inviter.
+     *
+     * @param decline the rejection to an invitation from another user to a room.
+     */
+    public void setDecline(Decline decline) {
+        this.decline = decline;
+    }
+
+    /**
+     * Sets the item child that holds information about roles, affiliation, jids and nicks.
+     *
+     * @param item the item child that holds information about roles, affiliation, jids and nicks.
+     */
+    public void setItem(Item item) {
+        this.item = item;
+    }
+
+    /**
+     * Sets the password to use to enter Password-Protected Room. A Password-Protected Room is
+     * a room that a user cannot enter without first providing the correct password.
+     *
+     * @param string the password to use to enter Password-Protected Room.
+     */
+    public void setPassword(String string) {
+        password = string;
+    }
+
+    /**
+     * Sets the status which holds a code that assists in presenting notification messages.
+     *
+     * @param status the status which holds a code that assists in presenting notification
+     * messages.
+     */
+    public void setStatus(Status status) {
+        this.status = status;
+    }
+
+    /**
+     * Sets the notification that the room has been destroyed. After a room has been destroyed,
+     * the room occupants will receive a Presence packet of type 'unavailable' with the reason for
+     * the room destruction if provided by the room owner.
+     *
+     * @param destroy the notification that the room has been destroyed.
+     */
+    public void setDestroy(Destroy destroy) {
+        this.destroy = destroy;
+    }
+
+    /**
+     * Represents an invitation for another user to a room. The sender of the invitation
+     * must be an occupant of the room. The invitation will be sent to the room which in turn
+     * will forward the invitation to the invitee.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Invite {
+        private String reason;
+        private String from;
+        private String to;
+
+        /**
+         * Returns the bare JID of the inviter or, optionally, the room JID. (e.g.
+         * 'crone1@shakespeare.lit/desktop').
+         *
+         * @return the room's occupant that sent the invitation.
+         */
+        public String getFrom() {
+            return from;
+        }
+
+        /**
+         * Returns the message explaining the invitation.
+         *
+         * @return the message explaining the invitation.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Returns the bare JID of the invitee. (e.g. 'hecate@shakespeare.lit')
+         *
+         * @return the bare JID of the invitee.
+         */
+        public String getTo() {
+            return to;
+        }
+
+        /**
+         * Sets the bare JID of the inviter or, optionally, the room JID. (e.g.
+         * 'crone1@shakespeare.lit/desktop')
+         *
+         * @param from the bare JID of the inviter or, optionally, the room JID.
+         */
+        public void setFrom(String from) {
+            this.from = from;
+        }
+
+        /**
+         * Sets the message explaining the invitation.
+         *
+         * @param reason the message explaining the invitation.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        /**
+         * Sets the bare JID of the invitee. (e.g. 'hecate@shakespeare.lit')
+         *
+         * @param to the bare JID of the invitee.
+         */
+        public void setTo(String to) {
+            this.to = to;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<invite ");
+            if (getTo() != null) {
+                buf.append(" to=\"").append(getTo()).append("\"");
+            }
+            if (getFrom() != null) {
+                buf.append(" from=\"").append(getFrom()).append("\"");
+            }
+            buf.append(">");
+            if (getReason() != null) {
+                buf.append("<reason>").append(getReason()).append("</reason>");
+            }
+            buf.append("</invite>");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Represents a rejection to an invitation from another user to a room. The rejection will be
+     * sent to the room which in turn will forward the refusal to the inviter.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Decline {
+        private String reason;
+        private String from;
+        private String to;
+
+        /**
+         * Returns the bare JID of the invitee that rejected the invitation. (e.g.
+         * 'crone1@shakespeare.lit/desktop').
+         *
+         * @return the bare JID of the invitee that rejected the invitation.
+         */
+        public String getFrom() {
+            return from;
+        }
+
+        /**
+         * Returns the message explaining why the invitation was rejected.
+         *
+         * @return the message explaining the reason for the rejection.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Returns the bare JID of the inviter. (e.g. 'hecate@shakespeare.lit')
+         *
+         * @return the bare JID of the inviter.
+         */
+        public String getTo() {
+            return to;
+        }
+
+        /**
+         * Sets the bare JID of the invitee that rejected the invitation. (e.g.
+         * 'crone1@shakespeare.lit/desktop').
+         *
+         * @param from the bare JID of the invitee that rejected the invitation.
+         */
+        public void setFrom(String from) {
+            this.from = from;
+        }
+
+        /**
+         * Sets the message explaining why the invitation was rejected.
+         *
+         * @param reason the message explaining the reason for the rejection.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        /**
+         * Sets the bare JID of the inviter. (e.g. 'hecate@shakespeare.lit')
+         *
+         * @param to the bare JID of the inviter.
+         */
+        public void setTo(String to) {
+            this.to = to;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<decline ");
+            if (getTo() != null) {
+                buf.append(" to=\"").append(getTo()).append("\"");
+            }
+            if (getFrom() != null) {
+                buf.append(" from=\"").append(getFrom()).append("\"");
+            }
+            buf.append(">");
+            if (getReason() != null) {
+                buf.append("<reason>").append(getReason()).append("</reason>");
+            }
+            buf.append("</decline>");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Item child that holds information about roles, affiliation, jids and nicks.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Item {
+        private String actor;
+        private String reason;
+        private String affiliation;
+        private String jid;
+        private String nick;
+        private String role;
+
+        /**
+         * Creates a new item child.
+         *
+         * @param affiliation the actor's affiliation to the room
+         * @param role the privilege level of an occupant within a room.
+         */
+        public Item(String affiliation, String role) {
+            this.affiliation = affiliation;
+            this.role = role;
+        }
+
+        /**
+         * Returns the actor (JID of an occupant in the room) that was kicked or banned.
+         *
+         * @return the JID of an occupant in the room that was kicked or banned.
+         */
+        public String getActor() {
+            return actor == null ? "" : actor;
+        }
+
+        /**
+         * Returns the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         *
+         * @return the reason for the item child.
+         */
+        public String getReason() {
+            return reason == null ? "" : reason;
+        }
+
+        /**
+         * Returns the occupant's affiliation to the room. The affiliation is a semi-permanent
+         * association or connection with a room. The possible affiliations are "owner", "admin",
+         * "member", and "outcast" (naturally it is also possible to have no affiliation). An
+         * affiliation lasts across a user's visits to a room.
+         *
+         * @return the actor's affiliation to the room
+         */
+        public String getAffiliation() {
+            return affiliation;
+        }
+
+        /**
+         * Returns the <room@service/nick> by which an occupant is identified within the context
+         * of a room. If the room is non-anonymous, the JID will be included in the item.
+         *
+         * @return the room JID by which an occupant is identified within the room.
+         */
+        public String getJid() {
+            return jid;
+        }
+
+        /**
+         * Returns the new nickname of an occupant that is changing his/her nickname. The new
+         * nickname is sent as part of the unavailable presence.
+         *
+         * @return the new nickname of an occupant that is changing his/her nickname.
+         */
+        public String getNick() {
+            return nick;
+        }
+
+        /**
+         * Returns the temporary position or privilege level of an occupant within a room. The
+         * possible roles are "moderator", "participant", and "visitor" (it is also possible to
+         * have no defined role). A role lasts only for the duration of an occupant's visit to
+         * a room.
+         *
+         * @return the privilege level of an occupant within a room.
+         */
+        public String getRole() {
+            return role;
+        }
+
+        /**
+         * Sets the actor (JID of an occupant in the room) that was kicked or banned.
+         *
+         * @param actor the actor (JID of an occupant in the room) that was kicked or banned.
+         */
+        public void setActor(String actor) {
+            this.actor = actor;
+        }
+
+        /**
+         * Sets the reason for the item child. The reason is optional and could be used to
+         * explain the reason why a user (occupant) was kicked or banned.
+         *
+         * @param reason the reason why a user (occupant) was kicked or banned.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        /**
+         * Sets the <room@service/nick> by which an occupant is identified within the context
+         * of a room. If the room is non-anonymous, the JID will be included in the item.
+         *
+         * @param jid the JID by which an occupant is identified within a room.
+         */
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        /**
+         * Sets the new nickname of an occupant that is changing his/her nickname. The new
+         * nickname is sent as part of the unavailable presence.
+         *
+         * @param nick the new nickname of an occupant that is changing his/her nickname.
+         */
+        public void setNick(String nick) {
+            this.nick = nick;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item");
+            if (getAffiliation() != null) {
+                buf.append(" affiliation=\"").append(getAffiliation()).append("\"");
+            }
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getNick() != null) {
+                buf.append(" nick=\"").append(getNick()).append("\"");
+            }
+            if (getRole() != null) {
+                buf.append(" role=\"").append(getRole()).append("\"");
+            }
+            if (getReason() == null && getActor() == null) {
+                buf.append("/>");
+            }
+            else {
+                buf.append(">");
+                if (getReason() != null) {
+                    buf.append("<reason>").append(getReason()).append("</reason>");
+                }
+                if (getActor() != null) {
+                    buf.append("<actor jid=\"").append(getActor()).append("\"/>");
+                }
+                buf.append("</item>");
+            }
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Status code assists in presenting notification messages. The following link provides the
+     * list of existing error codes (@link http://www.jabber.org/jeps/jep-0045.html#errorstatus).
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Status {
+        private String code;
+
+        /**
+         * Creates a new instance of Status with the specified code.
+         *
+         * @param code the code that uniquely identifies the reason of the error.
+         */
+        public Status(String code) {
+            this.code = code;
+        }
+
+        /**
+         * Returns the code that uniquely identifies the reason of the error. The code
+         * assists in presenting notification messages.
+         *
+         * @return the code that uniquely identifies the reason of the error.
+         */
+        public String getCode() {
+            return code;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<status code=\"").append(getCode()).append("\"/>");
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Represents a notification that the room has been destroyed. After a room has been destroyed,
+     * the room occupants will receive a Presence packet of type 'unavailable' with the reason for
+     * the room destruction if provided by the room owner.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Destroy {
+        private String reason;
+        private String jid;
+
+
+        /**
+         * Returns the JID of an alternate location since the current room is being destroyed.
+         *
+         * @return the JID of an alternate location.
+         */
+        public String getJid() {
+            return jid;
+        }
+
+        /**
+         * Returns the reason for the room destruction.
+         *
+         * @return the reason for the room destruction.
+         */
+        public String getReason() {
+            return reason;
+        }
+
+        /**
+         * Sets the JID of an alternate location since the current room is being destroyed.
+         *
+         * @param jid the JID of an alternate location.
+         */
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        /**
+         * Sets the reason for the room destruction.
+         *
+         * @param reason the reason for the room destruction.
+         */
+        public void setReason(String reason) {
+            this.reason = reason;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<destroy");
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getReason() == null) {
+                buf.append("/>");
+            }
+            else {
+                buf.append(">");
+                if (getReason() != null) {
+                    buf.append("<reason>").append(getReason()).append("</reason>");
+                }
+                buf.append("</destroy>");
+            }
+            return buf.toString();
+        }
+
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/packet/MessageEvent.java b/src/org/jivesoftware/smackx/packet/MessageEvent.java
new file mode 100644
index 0000000..5e146dc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MessageEvent.java
@@ -0,0 +1,335 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+
+/**
+ * Represents message events relating to the delivery, display, composition and cancellation of 
+ * messages.<p>
+ * 
+ * There are four message events currently defined in this namespace:
+ * <ol>
+ * <li>Offline<br>
+ * Indicates that the message has been stored offline by the intended recipient's server. This 
+ * event is triggered only if the intended recipient's server supports offline storage, has that 
+ * support enabled, and the recipient is offline when the server receives the message for delivery.</li>
+ * 
+ * <li>Delivered<br>
+ * Indicates that the message has been delivered to the recipient. This signifies that the message
+ * has reached the recipient's XMPP client, but does not necessarily mean that the message has 
+ * been displayed. This event is to be raised by the XMPP client.</li>
+ * 
+ * <li>Displayed<br>
+ * Once the message has been received by the recipient's XMPP client, it may be displayed to the
+ * user. This event indicates that the message has been displayed, and is to be raised by the 
+ * XMPP client. Even if a message is displayed multiple times, this event should be raised only 
+ * once.</li>
+ * 
+ * <li>Composing<br>
+ * In threaded chat conversations, this indicates that the recipient is composing a reply to a 
+ * message. The event is to be raised by the recipient's XMPP client. A XMPP client is allowed
+ * to raise this event multiple times in response to the same request, providing the original 
+ * event is cancelled first.</li>
+ * </ol>
+ *
+ * @author Gaston Dombiak
+ */
+public class MessageEvent implements PacketExtension {
+
+    public static final String OFFLINE = "offline";
+    public static final String COMPOSING = "composing";
+    public static final String DISPLAYED = "displayed";
+    public static final String DELIVERED = "delivered";
+    public static final String CANCELLED = "cancelled";
+
+    private boolean offline = false;
+    private boolean delivered = false;
+    private boolean displayed = false;
+    private boolean composing = false;
+    private boolean cancelled = true;
+
+    private String packetID = null;
+
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "x"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "x";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "jabber:x:event"
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "jabber:x:event";
+    }
+
+    /**
+     * When the message is a request returns if the sender of the message requests to be notified
+     * when the receiver is composing a reply.
+     * When the message is a notification returns if the receiver of the message is composing a 
+     * reply.
+     * 
+     * @return true if the sender is requesting to be notified when composing or when notifying
+     * that the receiver of the message is composing a reply
+     */
+    public boolean isComposing() {
+        return composing;
+    }
+
+    /**
+     * When the message is a request returns if the sender of the message requests to be notified
+     * when the message is delivered.
+     * When the message is a notification returns if the message was delivered or not.
+     * 
+     * @return true if the sender is requesting to be notified when delivered or when notifying 
+     * that the message was delivered 
+     */
+    public boolean isDelivered() {
+        return delivered;
+    }
+
+    /**
+     * When the message is a request returns if the sender of the message requests to be notified
+     * when the message is displayed.
+     * When the message is a notification returns if the message was displayed or not.
+     * 
+     * @return true if the sender is requesting to be notified when displayed or when notifying 
+     * that the message was displayed
+     */
+    public boolean isDisplayed() {
+        return displayed;
+    }
+
+    /**
+     * When the message is a request returns if the sender of the message requests to be notified
+     * when the receiver of the message is offline.
+     * When the message is a notification returns if the receiver of the message was offline.
+     * 
+     * @return true if the sender is requesting to be notified when offline or when notifying 
+     * that the receiver of the message is offline
+     */
+    public boolean isOffline() {
+        return offline;
+    }
+
+    /**
+     * When the message is a notification returns if the receiver of the message cancelled 
+     * composing a reply.
+     * 
+     * @return true if the receiver of the message cancelled composing a reply
+     */
+    public boolean isCancelled() {
+        return cancelled;
+    }
+
+    /**
+     * Returns the unique ID of the message that requested to be notified of the event.
+     * The packet id is not used when the message is a request for notifications
+     *
+     * @return the message id that requested to be notified of the event.
+     */
+    public String getPacketID() {
+        return packetID;
+    }
+
+    /**
+     * Returns the types of events. The type of event could be:
+     * "offline", "composing","delivered","displayed", "offline"
+     *
+     * @return an iterator over all the types of events of the MessageEvent.
+     */
+    public Iterator<String> getEventTypes() {
+        ArrayList<String> allEvents = new ArrayList<String>();
+        if (isDelivered()) {
+            allEvents.add(MessageEvent.DELIVERED);
+        }
+        if (!isMessageEventRequest() && isCancelled()) {
+            allEvents.add(MessageEvent.CANCELLED);
+        }
+        if (isComposing()) {
+            allEvents.add(MessageEvent.COMPOSING);
+        }
+        if (isDisplayed()) {
+            allEvents.add(MessageEvent.DISPLAYED);
+        }
+        if (isOffline()) {
+            allEvents.add(MessageEvent.OFFLINE);
+        }
+        return allEvents.iterator();
+    }
+
+    /**
+     * When the message is a request sets if the sender of the message requests to be notified
+     * when the receiver is composing a reply.
+     * When the message is a notification sets if the receiver of the message is composing a 
+     * reply.
+     * 
+     * @param composing sets if the sender is requesting to be notified when composing or when 
+     * notifying that the receiver of the message is composing a reply
+     */
+    public void setComposing(boolean composing) {
+        this.composing = composing;
+        setCancelled(false);
+    }
+
+    /**
+     * When the message is a request sets if the sender of the message requests to be notified
+     * when the message is delivered.
+     * When the message is a notification sets if the message was delivered or not.
+     * 
+     * @param delivered sets if the sender is requesting to be notified when delivered or when 
+     * notifying that the message was delivered 
+     */
+    public void setDelivered(boolean delivered) {
+        this.delivered = delivered;
+        setCancelled(false);
+    }
+
+    /**
+     * When the message is a request sets if the sender of the message requests to be notified
+     * when the message is displayed.
+     * When the message is a notification sets if the message was displayed or not.
+     * 
+     * @param displayed sets if the sender is requesting to be notified when displayed or when 
+     * notifying that the message was displayed
+     */
+    public void setDisplayed(boolean displayed) {
+        this.displayed = displayed;
+        setCancelled(false);
+    }
+
+    /**
+     * When the message is a request sets if the sender of the message requests to be notified
+     * when the receiver of the message is offline.
+     * When the message is a notification sets if the receiver of the message was offline.
+     * 
+     * @param offline sets if the sender is requesting to be notified when offline or when 
+     * notifying that the receiver of the message is offline
+     */
+    public void setOffline(boolean offline) {
+        this.offline = offline;
+        setCancelled(false);
+    }
+
+    /**
+     * When the message is a notification sets if the receiver of the message cancelled 
+     * composing a reply.
+     * The Cancelled event is never requested explicitly. It is requested implicitly when
+     * requesting to be notified of the Composing event.
+     * 
+     * @param cancelled sets if the receiver of the message cancelled composing a reply
+     */
+    public void setCancelled(boolean cancelled) {
+        this.cancelled = cancelled;
+    }
+
+    /**
+     * Sets the unique ID of the message that requested to be notified of the event.
+     * The packet id is not used when the message is a request for notifications
+     *
+     * @param packetID the message id that requested to be notified of the event.
+     */
+    public void setPacketID(String packetID) {
+        this.packetID = packetID;
+    }
+
+    /**
+     * Returns true if this MessageEvent is a request for notifications.
+     * Returns false if this MessageEvent is a notification of an event.
+     *
+    * @return true if this message is a request for notifications.
+     */
+    public boolean isMessageEventRequest() {
+        return this.packetID == null;
+    }
+
+    /**
+     * Returns the XML representation of a Message Event according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following examples:<p>
+     * 
+     * Request to be notified when displayed:
+     * <pre>
+     * &lt;message
+     *    to='romeo@montague.net/orchard'
+     *    from='juliet@capulet.com/balcony'
+     *    id='message22'&gt;
+     * &lt;x xmlns='jabber:x:event'&gt;
+     *   &lt;displayed/&gt;
+     * &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     * Notification of displayed:
+     * <pre>
+     * &lt;message
+     *    from='romeo@montague.net/orchard'
+     *    to='juliet@capulet.com/balcony'&gt;
+     * &lt;x xmlns='jabber:x:event'&gt;
+     *   &lt;displayed/&gt;
+     *   &lt;id&gt;message22&lt;/id&gt;
+     * &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        // Note: Cancellation events don't specify any tag. They just send the packetID
+
+        // Add the offline tag if the sender requests to be notified of offline events or if 
+        // the target is offline
+        if (isOffline())
+            buf.append("<").append(MessageEvent.OFFLINE).append("/>");
+        // Add the delivered tag if the sender requests to be notified when the message is 
+        // delivered or if the target notifies that the message has been delivered
+        if (isDelivered())
+            buf.append("<").append(MessageEvent.DELIVERED).append("/>");
+        // Add the displayed tag if the sender requests to be notified when the message is 
+        // displayed or if the target notifies that the message has been displayed
+        if (isDisplayed())
+            buf.append("<").append(MessageEvent.DISPLAYED).append("/>");
+        // Add the composing tag if the sender requests to be notified when the target is 
+        // composing a reply or if the target notifies that he/she is composing a reply
+        if (isComposing())
+            buf.append("<").append(MessageEvent.COMPOSING).append("/>");
+        // Add the id tag only if the MessageEvent is a notification message (not a request)
+        if (getPacketID() != null)
+            buf.append("<id>").append(getPacketID()).append("</id>");
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/MultipleAddresses.java b/src/org/jivesoftware/smackx/packet/MultipleAddresses.java
new file mode 100644
index 0000000..522250a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/MultipleAddresses.java
@@ -0,0 +1,205 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Packet extension that contains the list of addresses that a packet should be sent or was sent.
+ *
+ * @author Gaston Dombiak
+ */
+public class MultipleAddresses implements PacketExtension {
+
+    public static final String BCC = "bcc";
+    public static final String CC = "cc";
+    public static final String NO_REPLY = "noreply";
+    public static final String REPLY_ROOM = "replyroom";
+    public static final String REPLY_TO = "replyto";
+    public static final String TO = "to";
+
+
+    private List<Address> addresses = new ArrayList<Address>();
+
+    /**
+     * Adds a new address to which the packet is going to be sent or was sent.
+     *
+     * @param type on of the static type (BCC, CC, NO_REPLY, REPLY_ROOM, etc.)
+     * @param jid the JID address of the recipient.
+     * @param node used to specify a sub-addressable unit at a particular JID, corresponding to
+     *             a Service Discovery node.
+     * @param desc used to specify human-readable information for this address.
+     * @param delivered true when the packet was already delivered to this address.
+     * @param uri used to specify an external system address, such as a sip:, sips:, or im: URI.
+     */
+    public void addAddress(String type, String jid, String node, String desc, boolean delivered,
+            String uri) {
+        // Create a new address with the specificed configuration
+        Address address = new Address(type);
+        address.setJid(jid);
+        address.setNode(node);
+        address.setDescription(desc);
+        address.setDelivered(delivered);
+        address.setUri(uri);
+        // Add the new address to the list of multiple recipients
+        addresses.add(address);
+    }
+
+    /**
+     * Indicate that the packet being sent should not be replied.
+     */
+    public void setNoReply() {
+        // Create a new address with the specificed configuration
+        Address address = new Address(NO_REPLY);
+        // Add the new address to the list of multiple recipients
+        addresses.add(address);
+    }
+
+    /**
+     * Returns the list of addresses that matches the specified type. Examples of address
+     * type are: TO, CC, BCC, etc..
+     *
+     * @param type Examples of address type are: TO, CC, BCC, etc.
+     * @return the list of addresses that matches the specified type.
+     */
+    public List<Address> getAddressesOfType(String type) {
+        List<Address> answer = new ArrayList<Address>(addresses.size());
+        for (Iterator<Address> it = addresses.iterator(); it.hasNext();) {
+            Address address = (Address) it.next();
+            if (address.getType().equals(type)) {
+                answer.add(address);
+            }
+        }
+
+        return answer;
+    }
+
+    public String getElementName() {
+        return "addresses";
+    }
+
+    public String getNamespace() {
+        return "http://jabber.org/protocol/address";
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName());
+        buf.append(" xmlns=\"").append(getNamespace()).append("\">");
+        // Loop through all the addresses and append them to the string buffer
+        for (Iterator<Address> i = addresses.iterator(); i.hasNext();) {
+            Address address = (Address) i.next();
+            buf.append(address.toXML());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    public static class Address {
+
+        private String type;
+        private String jid;
+        private String node;
+        private String description;
+        private boolean delivered;
+        private String uri;
+
+        private Address(String type) {
+            this.type = type;
+        }
+
+        public String getType() {
+            return type;
+        }
+
+        public String getJid() {
+            return jid;
+        }
+
+        private void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        public String getNode() {
+            return node;
+        }
+
+        private void setNode(String node) {
+            this.node = node;
+        }
+
+        public String getDescription() {
+            return description;
+        }
+
+        private void setDescription(String description) {
+            this.description = description;
+        }
+
+        public boolean isDelivered() {
+            return delivered;
+        }
+
+        private void setDelivered(boolean delivered) {
+            this.delivered = delivered;
+        }
+
+        public String getUri() {
+            return uri;
+        }
+
+        private void setUri(String uri) {
+            this.uri = uri;
+        }
+
+        private String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<address type=\"");
+            // Append the address type (e.g. TO/CC/BCC)
+            buf.append(type).append("\"");
+            if (jid != null) {
+                buf.append(" jid=\"");
+                buf.append(jid).append("\"");
+            }
+            if (node != null) {
+                buf.append(" node=\"");
+                buf.append(node).append("\"");
+            }
+            if (description != null && description.trim().length() > 0) {
+                buf.append(" desc=\"");
+                buf.append(description).append("\"");
+            }
+            if (delivered) {
+                buf.append(" delivered=\"true\"");
+            }
+            if (uri != null) {
+                buf.append(" uri=\"");
+                buf.append(uri).append("\"");
+            }
+            buf.append("/>");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/Nick.java b/src/org/jivesoftware/smackx/packet/Nick.java
new file mode 100644
index 0000000..9a64eaa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/Nick.java
@@ -0,0 +1,112 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * A minimalistic implementation of a {@link PacketExtension} for nicknames.
+ * 
+ * @author Guus der Kinderen, guus.der.kinderen@gmail.com
+ * @see <a href="http://xmpp.org/extensions/xep-0172.html">XEP-0172: User Nickname</a>
+ */
+public class Nick implements PacketExtension {
+
+	public static final String NAMESPACE = "http://jabber.org/protocol/nick";
+
+	public static final String ELEMENT_NAME = "nick";
+
+	private String name = null;
+
+	public Nick(String name) {
+		this.name = name;
+	}
+
+	/**
+	 * The value of this nickname
+	 * 
+	 * @return the nickname
+	 */
+	public String getName() {
+		return name;
+	}
+
+	/**
+	 * Sets the value of this nickname
+	 * 
+	 * @param name
+	 *            the name to set
+	 */
+	public void setName(String name) {
+		this.name = name;
+	}
+
+	/*
+	 * (non-Javadoc)
+	 * 
+	 * @see org.jivesoftware.smack.packet.PacketExtension#getElementName()
+	 */
+	public String getElementName() {
+		return ELEMENT_NAME;
+	}
+
+	/*
+	 * (non-Javadoc)
+	 * 
+	 * @see org.jivesoftware.smack.packet.PacketExtension#getNamespace()
+	 */
+	public String getNamespace() {
+		return NAMESPACE;
+	}
+
+	/*
+	 * (non-Javadoc)
+	 * 
+	 * @see org.jivesoftware.smack.packet.PacketExtension#toXML()
+	 */
+	public String toXML() {
+		final StringBuilder buf = new StringBuilder();
+
+		buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(
+				NAMESPACE).append("\">");
+		buf.append(getName());
+		buf.append("</").append(ELEMENT_NAME).append('>');
+
+		return buf.toString();
+	}
+
+	public static class Provider implements PacketExtensionProvider {
+
+		public PacketExtension parseExtension(XmlPullParser parser)
+				throws Exception {
+			
+            parser.next();
+			final String name = parser.getText();
+
+			// Advance to end of extension.
+			while(parser.getEventType() != XmlPullParser.END_TAG) {
+				parser.next();
+			}
+
+			return new Nick(name);
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/packet/OfflineMessageInfo.java b/src/org/jivesoftware/smackx/packet/OfflineMessageInfo.java
new file mode 100644
index 0000000..5f9954d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/OfflineMessageInfo.java
@@ -0,0 +1,128 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * OfflineMessageInfo is an extension included in the retrieved offline messages requested by
+ * the {@link org.jivesoftware.smackx.OfflineMessageManager}. This extension includes a stamp
+ * that uniquely identifies the offline message. This stamp may be used for deleting the offline
+ * message. The stamp may be of the form UTC timestamps but it is not required to have that format.
+ *
+ * @author Gaston Dombiak
+ */
+public class OfflineMessageInfo implements PacketExtension {
+
+    private String node = null;
+
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "offline"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "offline";
+    }
+
+    /**
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "http://jabber.org/protocol/offline"
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "http://jabber.org/protocol/offline";
+    }
+
+    /**
+     * Returns the stamp that uniquely identifies the offline message. This stamp may
+     * be used for deleting the offline message. The stamp may be of the form UTC timestamps
+     * but it is not required to have that format.
+     *
+     * @return the stamp that uniquely identifies the offline message.
+     */
+    public String getNode() {
+        return node;
+    }
+
+    /**
+     * Sets the stamp that uniquely identifies the offline message. This stamp may
+     * be used for deleting the offline message. The stamp may be of the form UTC timestamps
+     * but it is not required to have that format.
+     *
+     * @param node the stamp that uniquely identifies the offline message.
+     */
+    public void setNode(String node) {
+        this.node = node;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        if (getNode() != null)
+            buf.append("<item node=\"").append(getNode()).append("\"/>");
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        /**
+         * Creates a new Provider.
+         * ProviderManager requires that every PacketExtensionProvider has a public,
+         * no-argument constructor
+         */
+        public Provider() {
+        }
+
+        /**
+         * Parses a OfflineMessageInfo packet (extension sub-packet).
+         *
+         * @param parser the XML parser, positioned at the starting element of the extension.
+         * @return a PacketExtension.
+         * @throws Exception if a parsing error occurs.
+         */
+        public PacketExtension parseExtension(XmlPullParser parser)
+            throws Exception {
+            OfflineMessageInfo info = new OfflineMessageInfo();
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("item"))
+                        info.setNode(parser.getAttributeValue("", "node"));
+                } else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("offline")) {
+                        done = true;
+                    }
+                }
+            }
+
+            return info;
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/OfflineMessageRequest.java b/src/org/jivesoftware/smackx/packet/OfflineMessageRequest.java
new file mode 100644
index 0000000..1d9d096
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/OfflineMessageRequest.java
@@ -0,0 +1,237 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents a request to get some or all the offline messages of a user. This class can also
+ * be used for deleting some or all the offline messages of a user.
+ *
+ * @author Gaston Dombiak
+ */
+public class OfflineMessageRequest extends IQ {
+
+    private List<Item> items = new ArrayList<Item>();
+    private boolean purge = false;
+    private boolean fetch = false;
+
+    /**
+     * Returns an Iterator for item childs that holds information about offline messages to
+     * view or delete.
+     *
+     * @return an Iterator for item childs that holds information about offline messages to
+     *         view or delete.
+     */
+    public Iterator<Item> getItems() {
+        synchronized (items) {
+            return Collections.unmodifiableList(new ArrayList<Item>(items)).iterator();
+        }
+    }
+
+    /**
+     * Adds an item child that holds information about offline messages to view or delete.
+     *
+     * @param item the item child that holds information about offline messages to view or delete.
+     */
+    public void addItem(Item item) {
+        synchronized (items) {
+            items.add(item);
+        }
+    }
+
+    /**
+     * Returns true if all the offline messages of the user should be deleted.
+     *
+     * @return true if all the offline messages of the user should be deleted.
+     */
+    public boolean isPurge() {
+        return purge;
+    }
+
+    /**
+     * Sets if all the offline messages of the user should be deleted.
+     *
+     * @param purge true if all the offline messages of the user should be deleted.
+     */
+    public void setPurge(boolean purge) {
+        this.purge = purge;
+    }
+
+    /**
+     * Returns true if all the offline messages of the user should be retrieved.
+     *
+     * @return true if all the offline messages of the user should be retrieved.
+     */
+    public boolean isFetch() {
+        return fetch;
+    }
+
+    /**
+     * Sets if all the offline messages of the user should be retrieved.
+     *
+     * @param fetch true if all the offline messages of the user should be retrieved.
+     */
+    public void setFetch(boolean fetch) {
+        this.fetch = fetch;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<offline xmlns=\"http://jabber.org/protocol/offline\">");
+        synchronized (items) {
+            for (int i = 0; i < items.size(); i++) {
+                Item item = items.get(i);
+                buf.append(item.toXML());
+            }
+        }
+        if (purge) {
+            buf.append("<purge/>");
+        }
+        if (fetch) {
+            buf.append("<fetch/>");
+        }
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</offline>");
+        return buf.toString();
+    }
+
+    /**
+     * Item child that holds information about offline messages to view or delete.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Item {
+        private String action;
+        private String jid;
+        private String node;
+
+        /**
+         * Creates a new item child.
+         *
+         * @param node the actor's affiliation to the room
+         */
+        public Item(String node) {
+            this.node = node;
+        }
+
+        public String getNode() {
+            return node;
+        }
+
+        /**
+         * Returns "view" or "remove" that indicate if the server should return the specified
+         * offline message or delete it.
+         *
+         * @return "view" or "remove" that indicate if the server should return the specified
+         *         offline message or delete it.
+         */
+        public String getAction() {
+            return action;
+        }
+
+        /**
+         * Sets if the server should return the specified offline message or delete it. Possible
+         * values are "view" or "remove".
+         *
+         * @param action if the server should return the specified offline message or delete it.
+         */
+        public void setAction(String action) {
+            this.action = action;
+        }
+
+        public String getJid() {
+            return jid;
+        }
+
+        public void setJid(String jid) {
+            this.jid = jid;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<item");
+            if (getAction() != null) {
+                buf.append(" action=\"").append(getAction()).append("\"");
+            }
+            if (getJid() != null) {
+                buf.append(" jid=\"").append(getJid()).append("\"");
+            }
+            if (getNode() != null) {
+                buf.append(" node=\"").append(getNode()).append("\"");
+            }
+            buf.append("/>");
+            return buf.toString();
+        }
+    }
+
+    public static class Provider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            OfflineMessageRequest request = new OfflineMessageRequest();
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("item")) {
+                        request.addItem(parseItem(parser));
+                    }
+                    else if (parser.getName().equals("purge")) {
+                        request.setPurge(true);
+                    }
+                    else if (parser.getName().equals("fetch")) {
+                        request.setFetch(true);
+                    }
+                } else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("offline")) {
+                        done = true;
+                    }
+                }
+            }
+
+            return request;
+        }
+
+        private Item parseItem(XmlPullParser parser) throws Exception {
+            boolean done = false;
+            Item item = new Item(parser.getAttributeValue("", "node"));
+            item.setAction(parser.getAttributeValue("", "action"));
+            item.setJid(parser.getAttributeValue("", "jid"));
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("item")) {
+                        done = true;
+                    }
+                }
+            }
+            return item;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/PEPEvent.java b/src/org/jivesoftware/smackx/packet/PEPEvent.java
new file mode 100644
index 0000000..48f1de2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/PEPEvent.java
@@ -0,0 +1,105 @@
+/**
+ * $RCSfile: PEPEvent.java,v $
+ * $Revision: 1.1 $
+ * $Date: 2007/11/03 00:14:32 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents XMPP Personal Event Protocol packets.<p>
+ * 
+ * The 'http://jabber.org/protocol/pubsub#event' namespace  is used to publish personal events items from one client 
+ * to subscribed clients (See XEP-163).
+ *
+ * @author Jeff Williams
+ */
+public class PEPEvent implements PacketExtension {
+
+    PEPItem item;
+
+    /**
+     * Creates a new empty roster exchange package.
+     *
+     */
+    public PEPEvent() {
+        super();
+    }
+
+    /**
+     * Creates a new empty roster exchange package.
+     *
+     */
+    public PEPEvent(PEPItem item) {
+        super();
+
+        this.item = item;
+    }
+    
+    public void addPEPItem(PEPItem item) {
+        this.item = item;
+    }
+
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "x"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "event";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "jabber:x:roster"
+     * (which is not to be confused with the 'jabber:iq:roster' namespace
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "http://jabber.org/protocol/pubsub";
+    }
+
+    /**
+     * Returns the XML representation of a Personal Event Publish according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following example:
+     * <pre>
+     * &lt;message id="MlIpV-4" to="gato1@gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;subject&gt;Any subject you want&lt;/subject&gt;
+     *     &lt;body&gt;This message contains roster items.&lt;/body&gt;
+     *     &lt;x xmlns="jabber:x:roster"&gt;
+     *         &lt;item jid="gato1@gato.home"/&gt;
+     *         &lt;item jid="gato2@gato.home"/&gt;
+     *     &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append("\">");
+        buf.append(item.toXML());
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/PEPItem.java b/src/org/jivesoftware/smackx/packet/PEPItem.java
new file mode 100644
index 0000000..c3ff6f4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/PEPItem.java
@@ -0,0 +1,92 @@
+/**
+ * $RCSfile: PEPItem.java,v $
+ * $Revision: 1.2 $
+ * $Date: 2007/11/06 02:05:09 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents XMPP Personal Event Protocol packets.<p>
+ * 
+ * The 'http://jabber.org/protocol/pubsub#event' namespace  is used to publish personal events items from one client 
+ * to subscribed clients (See XEP-163).
+ *
+ * @author Jeff Williams
+ */
+public abstract class PEPItem implements PacketExtension {
+    
+    String id;
+    abstract String getNode();
+    abstract String getItemDetailsXML();
+    
+    /**
+    * Creates a new PEPItem.
+    *
+    */
+    public PEPItem(String id) {
+        super();
+        this.id = id;
+    }
+    
+     /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "x"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "item";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "http://jabber.org/protocol/pubsub";
+    }
+
+    /**
+     * Returns the XML representation of a Personal Event Publish according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following example:
+     * <pre>
+     * &lt;message id="MlIpV-4" to="gato1@gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;subject&gt;Any subject you want&lt;/subject&gt;
+     *     &lt;body&gt;This message contains roster items.&lt;/body&gt;
+     *     &lt;x xmlns="jabber:x:roster"&gt;
+     *         &lt;item jid="gato1@gato.home"/&gt;
+     *         &lt;item jid="gato2@gato.home"/&gt;
+     *     &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" id=\"").append(id).append("\">");
+        buf.append(getItemDetailsXML());
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/PEPPubSub.java b/src/org/jivesoftware/smackx/packet/PEPPubSub.java
new file mode 100644
index 0000000..420ce61
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/PEPPubSub.java
@@ -0,0 +1,95 @@
+/**
+ * $RCSfile: PEPPubSub.java,v $
+ * $Revision: 1.2 $
+ * $Date: 2007/11/03 04:46:52 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+/**
+ * Represents XMPP PEP/XEP-163 pubsub packets.<p>
+ * 
+ * The 'http://jabber.org/protocol/pubsub' namespace  is used to publish personal events items from one client 
+ * to subscribed clients (See XEP-163).
+ *
+ * @author Jeff Williams
+ */
+public class PEPPubSub extends IQ {
+    
+    PEPItem item;
+
+    /**
+    * Creates a new PubSub.
+    *
+    */
+    public PEPPubSub(PEPItem item) {
+        super();
+        
+        this.item = item;
+    }
+
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "x"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "pubsub";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "jabber:x:roster"
+     * (which is not to be confused with the 'jabber:iq:roster' namespace
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "http://jabber.org/protocol/pubsub";
+    }
+
+    /**
+     * Returns the XML representation of a Personal Event Publish according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following example:
+     * <pre>
+     * &lt;message id="MlIpV-4" to="gato1@gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;subject&gt;Any subject you want&lt;/subject&gt;
+     *     &lt;body&gt;This message contains roster items.&lt;/body&gt;
+     *     &lt;x xmlns="jabber:x:roster"&gt;
+     *         &lt;item jid="gato1@gato.home"/&gt;
+     *         &lt;item jid="gato2@gato.home"/&gt;
+     *     &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append("\">");
+        buf.append("<publish node=\"").append(item.getNode()).append("\">");
+        buf.append(item.toXML());
+        buf.append("</publish>");
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/PrivateData.java b/src/org/jivesoftware/smackx/packet/PrivateData.java
new file mode 100644
index 0000000..3ddb7d5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/PrivateData.java
@@ -0,0 +1,52 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+/**
+ * Interface to represent private data. Each private data chunk is an XML sub-document
+ * with a root element name and namespace.
+ *
+ * @see org.jivesoftware.smackx.PrivateDataManager
+ * @author Matt Tucker
+ */
+public interface PrivateData {
+
+    /**
+     * Returns the root element name.
+     *
+     * @return the element name.
+     */
+    public String getElementName();
+
+    /**
+     * Returns the root element XML namespace.
+     *
+     * @return the namespace.
+     */
+    public String getNamespace();
+
+    /**
+     * Returns the XML reppresentation of the PrivateData.
+     *
+     * @return the private data as XML.
+     */
+    public String toXML();
+}
diff --git a/src/org/jivesoftware/smackx/packet/RosterExchange.java b/src/org/jivesoftware/smackx/packet/RosterExchange.java
new file mode 100644
index 0000000..ad59146
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/RosterExchange.java
@@ -0,0 +1,181 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.Roster;
+import org.jivesoftware.smack.RosterEntry;
+import org.jivesoftware.smack.RosterGroup;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.RemoteRosterEntry;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents XMPP Roster Item Exchange packets.<p>
+ * 
+ * The 'jabber:x:roster' namespace (which is not to be confused with the 'jabber:iq:roster' 
+ * namespace) is used to send roster items from one client to another. A roster item is sent by 
+ * adding to the &lt;message/&gt; element an &lt;x/&gt; child scoped by the 'jabber:x:roster' namespace. This 
+ * &lt;x/&gt; element may contain one or more &lt;item/&gt; children (one for each roster item to be sent).<p>
+ * 
+ * Each &lt;item/&gt; element may possess the following attributes:<p>
+ * 
+ * &lt;jid/&gt; -- The id of the contact being sent. This attribute is required.<br>
+ * &lt;name/&gt; -- A natural-language nickname for the contact. This attribute is optional.<p>
+ * 
+ * Each &lt;item/&gt; element may also contain one or more &lt;group/&gt; children specifying the 
+ * natural-language name of a user-specified group, for the purpose of categorizing this contact 
+ * into one or more roster groups.
+ *
+ * @author Gaston Dombiak
+ */
+public class RosterExchange implements PacketExtension {
+
+    private List<RemoteRosterEntry> remoteRosterEntries = new ArrayList<RemoteRosterEntry>();
+
+    /**
+     * Creates a new empty roster exchange package.
+     *
+     */
+    public RosterExchange() {
+        super();
+    }
+
+    /**
+     * Creates a new roster exchange package with the entries specified in roster.
+     *
+     * @param roster the roster to send to other XMPP entity.
+     */
+    public RosterExchange(Roster roster) {
+        // Add all the roster entries to the new RosterExchange 
+        for (RosterEntry rosterEntry : roster.getEntries()) {
+            this.addRosterEntry(rosterEntry);
+        }
+    }
+
+    /**
+     * Adds a roster entry to the packet.
+     *
+     * @param rosterEntry a roster entry to add.
+     */
+    public void addRosterEntry(RosterEntry rosterEntry) {
+		// Obtain a String[] from the roster entry groups name 
+		List<String> groupNamesList = new ArrayList<String>();
+		String[] groupNames;
+		for (RosterGroup group : rosterEntry.getGroups()) {
+			groupNamesList.add(group.getName());
+		}
+		groupNames = groupNamesList.toArray(new String[groupNamesList.size()]);
+
+        // Create a new Entry based on the rosterEntry and add it to the packet
+        RemoteRosterEntry remoteRosterEntry = new RemoteRosterEntry(rosterEntry.getUser(),
+                rosterEntry.getName(), groupNames);
+		
+        addRosterEntry(remoteRosterEntry);
+    }
+
+    /**
+     * Adds a remote roster entry to the packet.
+     *
+     * @param remoteRosterEntry a remote roster entry to add.
+     */
+    public void addRosterEntry(RemoteRosterEntry remoteRosterEntry) {
+        synchronized (remoteRosterEntries) {
+            remoteRosterEntries.add(remoteRosterEntry);
+        }
+    }
+    
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "x"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "x";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "jabber:x:roster"
+     * (which is not to be confused with the 'jabber:iq:roster' namespace
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "jabber:x:roster";
+    }
+
+    /**
+     * Returns an Iterator for the roster entries in the packet.
+     *
+     * @return an Iterator for the roster entries in the packet.
+     */
+    public Iterator<RemoteRosterEntry> getRosterEntries() {
+        synchronized (remoteRosterEntries) {
+            List<RemoteRosterEntry> entries = Collections.unmodifiableList(new ArrayList<RemoteRosterEntry>(remoteRosterEntries));
+            return entries.iterator();
+        }
+    }
+
+    /**
+     * Returns a count of the entries in the roster exchange.
+     *
+     * @return the number of entries in the roster exchange.
+     */
+    public int getEntryCount() {
+        return remoteRosterEntries.size();
+    }
+
+    /**
+     * Returns the XML representation of a Roster Item Exchange according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following example:
+     * <pre>
+     * &lt;message id="MlIpV-4" to="gato1@gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;subject&gt;Any subject you want&lt;/subject&gt;
+     *     &lt;body&gt;This message contains roster items.&lt;/body&gt;
+     *     &lt;x xmlns="jabber:x:roster"&gt;
+     *         &lt;item jid="gato1@gato.home"/&gt;
+     *         &lt;item jid="gato2@gato.home"/&gt;
+     *     &lt;/x&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        // Loop through all roster entries and append them to the string buffer
+        for (Iterator<RemoteRosterEntry> i = getRosterEntries(); i.hasNext();) {
+            RemoteRosterEntry remoteRosterEntry = i.next();
+            buf.append(remoteRosterEntry.toXML());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/SharedGroupsInfo.java b/src/org/jivesoftware/smackx/packet/SharedGroupsInfo.java
new file mode 100644
index 0000000..59bd98e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/SharedGroupsInfo.java
@@ -0,0 +1,92 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * IQ packet used for discovering the user's shared groups and for getting the answer back
+ * from the server.<p>
+ *
+ * Important note: This functionality is not part of the XMPP spec and it will only work
+ * with Wildfire.
+ *
+ * @author Gaston Dombiak
+ */
+public class SharedGroupsInfo extends IQ {
+
+    private List<String> groups = new ArrayList<String>();
+
+    /**
+     * Returns a collection with the shared group names returned from the server.
+     *
+     * @return collection with the shared group names returned from the server.
+     */
+    public List<String> getGroups() {
+        return groups;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<sharedgroup xmlns=\"http://www.jivesoftware.org/protocol/sharedgroup\">");
+        for (Iterator<String> it=groups.iterator(); it.hasNext();) {
+            buf.append("<group>").append(it.next()).append("</group>");
+        }
+        buf.append("</sharedgroup>");
+        return buf.toString();
+    }
+
+    /**
+     * Internal Search service Provider.
+     */
+    public static class Provider implements IQProvider {
+
+        /**
+         * Provider Constructor.
+         */
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            SharedGroupsInfo groupsInfo = new SharedGroupsInfo();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG && parser.getName().equals("group")) {
+                    groupsInfo.getGroups().add(parser.nextText());
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("sharedgroup")) {
+                        done = true;
+                    }
+                }
+            }
+            return groupsInfo;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/StreamInitiation.java b/src/org/jivesoftware/smackx/packet/StreamInitiation.java
new file mode 100644
index 0000000..511a02c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/StreamInitiation.java
@@ -0,0 +1,419 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.packet;
+
+import java.util.Date;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * The process by which two entities initiate a stream.
+ *
+ * @author Alexander Wenckus
+ */
+public class StreamInitiation extends IQ {
+
+    private String id;
+
+    private String mimeType;
+
+    private File file;
+
+    private Feature featureNegotiation;
+
+    /**
+     * The "id" attribute is an opaque identifier. This attribute MUST be
+     * present on type='set', and MUST be a valid string. This SHOULD NOT be
+     * sent back on type='result', since the <iq/> "id" attribute provides the
+     * only context needed. This value is generated by the Sender, and the same
+     * value MUST be used throughout a session when talking to the Receiver.
+     *
+     * @param id The "id" attribute.
+     */
+    public void setSesssionID(final String id) {
+        this.id = id;
+    }
+
+    /**
+     * Uniquely identifies a stream initiation to the recipient.
+     *
+     * @return The "id" attribute.
+     * @see #setSesssionID(String)
+     */
+    public String getSessionID() {
+        return id;
+    }
+
+    /**
+     * The "mime-type" attribute identifies the MIME-type for the data across
+     * the stream. This attribute MUST be a valid MIME-type as registered with
+     * the Internet Assigned Numbers Authority (IANA) [3] (specifically, as
+     * listed at <http://www.iana.org/assignments/media-types>). During
+     * negotiation, this attribute SHOULD be present, and is otherwise not
+     * required. If not included during negotiation, its value is assumed to be
+     * "binary/octect-stream".
+     *
+     * @param mimeType The valid mime-type.
+     */
+    public void setMimeType(final String mimeType) {
+        this.mimeType = mimeType;
+    }
+
+    /**
+     * Identifies the type of file that is desired to be transfered.
+     *
+     * @return The mime-type.
+     * @see #setMimeType(String)
+     */
+    public String getMimeType() {
+        return mimeType;
+    }
+
+    /**
+     * Sets the file which contains the information pertaining to the file to be
+     * transfered.
+     *
+     * @param file The file identified by the stream initiator to be sent.
+     */
+    public void setFile(final File file) {
+        this.file = file;
+    }
+
+    /**
+     * Returns the file containing the information about the request.
+     *
+     * @return Returns the file containing the information about the request.
+     */
+    public File getFile() {
+        return file;
+    }
+
+    /**
+     * Sets the data form which contains the valid methods of stream neotiation
+     * and transfer.
+     *
+     * @param form The dataform containing the methods.
+     */
+    public void setFeatureNegotiationForm(final DataForm form) {
+        this.featureNegotiation = new Feature(form);
+    }
+
+    /**
+     * Returns the data form which contains the valid methods of stream
+     * neotiation and transfer.
+     *
+     * @return Returns the data form which contains the valid methods of stream
+     *         neotiation and transfer.
+     */
+    public DataForm getFeatureNegotiationForm() {
+        return featureNegotiation.getData();
+    }
+
+    /*
+      * (non-Javadoc)
+      *
+      * @see org.jivesoftware.smack.packet.IQ#getChildElementXML()
+      */
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        if (this.getType().equals(IQ.Type.SET)) {
+            buf.append("<si xmlns=\"http://jabber.org/protocol/si\" ");
+            if (getSessionID() != null) {
+                buf.append("id=\"").append(getSessionID()).append("\" ");
+            }
+            if (getMimeType() != null) {
+                buf.append("mime-type=\"").append(getMimeType()).append("\" ");
+            }
+            buf
+                    .append("profile=\"http://jabber.org/protocol/si/profile/file-transfer\">");
+
+            // Add the file section if there is one.
+            String fileXML = file.toXML();
+            if (fileXML != null) {
+                buf.append(fileXML);
+            }
+        }
+        else if (this.getType().equals(IQ.Type.RESULT)) {
+            buf.append("<si xmlns=\"http://jabber.org/protocol/si\">");
+        }
+        else {
+            throw new IllegalArgumentException("IQ Type not understood");
+        }
+        if (featureNegotiation != null) {
+            buf.append(featureNegotiation.toXML());
+        }
+        buf.append("</si>");
+        return buf.toString();
+    }
+
+    /**
+     * <ul>
+     * <li>size: The size, in bytes, of the data to be sent.</li>
+     * <li>name: The name of the file that the Sender wishes to send.</li>
+     * <li>date: The last modification time of the file. This is specified
+     * using the DateTime profile as described in Jabber Date and Time Profiles.</li>
+     * <li>hash: The MD5 sum of the file contents.</li>
+     * </ul>
+     * <p/>
+     * <p/>
+     * &lt;desc&gt; is used to provide a sender-generated description of the
+     * file so the receiver can better understand what is being sent. It MUST
+     * NOT be sent in the result.
+     * <p/>
+     * <p/>
+     * When &lt;range&gt; is sent in the offer, it should have no attributes.
+     * This signifies that the sender can do ranged transfers. When a Stream
+     * Initiation result is sent with the <range> element, it uses these
+     * attributes:
+     * <p/>
+     * <ul>
+     * <li>offset: Specifies the position, in bytes, to start transferring the
+     * file data from. This defaults to zero (0) if not specified.</li>
+     * <li>length - Specifies the number of bytes to retrieve starting at
+     * offset. This defaults to the length of the file from offset to the end.</li>
+     * </ul>
+     * <p/>
+     * <p/>
+     * Both attributes are OPTIONAL on the &lt;range&gt; element. Sending no
+     * attributes is synonymous with not sending the &lt;range&gt; element. When
+     * no &lt;range&gt; element is sent in the Stream Initiation result, the
+     * Sender MUST send the complete file starting at offset 0. More generally,
+     * data is sent over the stream byte for byte starting at the offset
+     * position for the length specified.
+     *
+     * @author Alexander Wenckus
+     */
+    public static class File implements PacketExtension {
+
+        private final String name;
+
+        private final long size;
+
+        private String hash;
+
+        private Date date;
+
+        private String desc;
+
+        private boolean isRanged;
+
+        /**
+         * Constructor providing the name of the file and its size.
+         *
+         * @param name The name of the file.
+         * @param size The size of the file in bytes.
+         */
+        public File(final String name, final long size) {
+            if (name == null) {
+                throw new NullPointerException("name cannot be null");
+            }
+
+            this.name = name;
+            this.size = size;
+        }
+
+        /**
+         * Returns the file's name.
+         *
+         * @return Returns the file's name.
+         */
+        public String getName() {
+            return name;
+        }
+
+        /**
+         * Returns the file's size.
+         *
+         * @return Returns the file's size.
+         */
+        public long getSize() {
+            return size;
+        }
+
+        /**
+         * Sets the MD5 sum of the file's contents
+         *
+         * @param hash The MD5 sum of the file's contents.
+         */
+        public void setHash(final String hash) {
+            this.hash = hash;
+        }
+
+        /**
+         * Returns the MD5 sum of the file's contents
+         *
+         * @return Returns the MD5 sum of the file's contents
+         */
+        public String getHash() {
+            return hash;
+        }
+
+        /**
+         * Sets the date that the file was last modified.
+         *
+         * @param date The date that the file was last modified.
+         */
+        public void setDate(Date date) {
+            this.date = date;
+        }
+
+        /**
+         * Returns the date that the file was last modified.
+         *
+         * @return Returns the date that the file was last modified.
+         */
+        public Date getDate() {
+            return date;
+        }
+
+        /**
+         * Sets the description of the file.
+         *
+         * @param desc The description of the file so that the file reciever can
+         *             know what file it is.
+         */
+        public void setDesc(final String desc) {
+            this.desc = desc;
+        }
+
+        /**
+         * Returns the description of the file.
+         *
+         * @return Returns the description of the file.
+         */
+        public String getDesc() {
+            return desc;
+        }
+
+        /**
+         * True if a range can be provided and false if it cannot.
+         *
+         * @param isRanged True if a range can be provided and false if it cannot.
+         */
+        public void setRanged(final boolean isRanged) {
+            this.isRanged = isRanged;
+        }
+
+        /**
+         * Returns whether or not the initiator can support a range for the file
+         * tranfer.
+         *
+         * @return Returns whether or not the initiator can support a range for
+         *         the file tranfer.
+         */
+        public boolean isRanged() {
+            return isRanged;
+        }
+
+        public String getElementName() {
+            return "file";
+        }
+
+        public String getNamespace() {
+            return "http://jabber.org/protocol/si/profile/file-transfer";
+        }
+
+        public String toXML() {
+            StringBuilder buffer = new StringBuilder();
+
+            buffer.append("<").append(getElementName()).append(" xmlns=\"")
+                    .append(getNamespace()).append("\" ");
+
+            if (getName() != null) {
+                buffer.append("name=\"").append(StringUtils.escapeForXML(getName())).append("\" ");
+            }
+
+            if (getSize() > 0) {
+                buffer.append("size=\"").append(getSize()).append("\" ");
+            }
+
+            if (getDate() != null) {
+                buffer.append("date=\"").append(StringUtils.formatXEP0082Date(date)).append("\" ");
+            }
+
+            if (getHash() != null) {
+                buffer.append("hash=\"").append(getHash()).append("\" ");
+            }
+
+            if ((desc != null && desc.length() > 0) || isRanged) {
+                buffer.append(">");
+                if (getDesc() != null && desc.length() > 0) {
+                    buffer.append("<desc>").append(StringUtils.escapeForXML(getDesc())).append("</desc>");
+                }
+                if (isRanged()) {
+                    buffer.append("<range/>");
+                }
+                buffer.append("</").append(getElementName()).append(">");
+            }
+            else {
+                buffer.append("/>");
+            }
+            return buffer.toString();
+        }
+    }
+
+    /**
+     * The feature negotiation portion of the StreamInitiation packet.
+     *
+     * @author Alexander Wenckus
+     *
+     */
+    public class Feature implements PacketExtension {
+
+        private final DataForm data;
+
+        /**
+         * The dataform can be provided as part of the constructor.
+         *
+         * @param data The dataform.
+         */
+        public Feature(final DataForm data) {
+            this.data = data;
+        }
+
+        /**
+         * Returns the dataform associated with the feature negotiation.
+         *
+         * @return Returns the dataform associated with the feature negotiation.
+         */
+        public DataForm getData() {
+            return data;
+        }
+
+        public String getNamespace() {
+            return "http://jabber.org/protocol/feature-neg";
+        }
+
+        public String getElementName() {
+            return "feature";
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+            buf
+                    .append("<feature xmlns=\"http://jabber.org/protocol/feature-neg\">");
+			buf.append(data.toXML());
+			buf.append("</feature>");
+			return buf.toString();
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/packet/Time.java b/src/org/jivesoftware/smackx/packet/Time.java
new file mode 100644
index 0000000..5294e77
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/Time.java
@@ -0,0 +1,198 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.Calendar;
+import java.util.Date;
+import java.util.TimeZone;
+
+/**
+ * A Time IQ packet, which is used by XMPP clients to exchange their respective local
+ * times. Clients that wish to fully support the entitity time protocol should register
+ * a PacketListener for incoming time requests that then respond with the local time.
+ * This class can be used to request the time from other clients, such as in the
+ * following code snippet:
+ *
+ * <pre>
+ * // Request the time from a remote user.
+ * Time timeRequest = new Time();
+ * timeRequest.setType(IQ.Type.GET);
+ * timeRequest.setTo(someUser@example.com/resource);
+ *
+ * // Create a packet collector to listen for a response.
+ * PacketCollector collector = con.createPacketCollector(
+ *                new PacketIDFilter(timeRequest.getPacketID()));
+ *
+ * con.sendPacket(timeRequest);
+ *
+ * // Wait up to 5 seconds for a result.
+ * IQ result = (IQ)collector.nextResult(5000);
+ * if (result != null && result.getType() == IQ.Type.RESULT) {
+ *     Time timeResult = (Time)result;
+ *     // Do something with result...
+ * }</pre><p>
+ *
+ * Warning: this is an non-standard protocol documented by
+ * <a href="http://www.xmpp.org/extensions/xep-0090.html">XEP-0090</a>. Because this is a
+ * non-standard protocol, it is subject to change.
+ *
+ * @author Matt Tucker
+ */
+public class Time extends IQ {
+
+    private static SimpleDateFormat utcFormat = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+    private static DateFormat displayFormat = DateFormat.getDateTimeInstance();
+
+    private String utc = null;
+    private String tz = null;
+    private String display = null;
+
+    /**
+     * Creates a new Time instance with empty values for all fields.
+     */
+    public Time() {
+        
+    }
+
+    /**
+     * Creates a new Time instance using the specified calendar instance as
+     * the time value to send.
+     *
+     * @param cal the time value.
+     */
+    public Time(Calendar cal) {
+        TimeZone timeZone = cal.getTimeZone();
+        tz = cal.getTimeZone().getID();
+        display = displayFormat.format(cal.getTime());
+        // Convert local time to the UTC time.
+        utc = utcFormat.format(new Date(
+                cal.getTimeInMillis() - timeZone.getOffset(cal.getTimeInMillis())));
+    }
+
+    /**
+     * Returns the local time or <tt>null</tt> if the time hasn't been set.
+     *
+     * @return the lcocal time.
+     */
+    public Date getTime() {
+        if (utc == null) {
+            return null;
+        }
+        Date date = null;
+        try {
+            Calendar cal = Calendar.getInstance();
+            // Convert the UTC time to local time.
+            cal.setTime(new Date(utcFormat.parse(utc).getTime() +
+                    cal.getTimeZone().getOffset(cal.getTimeInMillis())));
+            date = cal.getTime();
+        }
+        catch (Exception e) {
+            e.printStackTrace();
+        }
+        return date;
+    }
+
+    /**
+     * Sets the time using the local time.
+     *
+     * @param time the current local time.
+     */
+    public void setTime(Date time) {
+        // Convert local time to UTC time.
+        utc = utcFormat.format(new Date(
+                time.getTime() - TimeZone.getDefault().getOffset(time.getTime())));
+    }
+
+    /**
+     * Returns the time as a UTC formatted String using the format CCYYMMDDThh:mm:ss.
+     *
+     * @return the time as a UTC formatted String.
+     */
+    public String getUtc() {
+        return utc;
+    }
+
+    /**
+     * Sets the time using UTC formatted String in the format CCYYMMDDThh:mm:ss.
+     *
+     * @param utc the time using a formatted String.
+     */
+    public void setUtc(String utc) {
+        this.utc = utc;
+
+    }
+
+    /**
+     * Returns the time zone.
+     *
+     * @return the time zone.
+     */
+    public String getTz() {
+        return tz;
+    }
+
+    /**
+     * Sets the time zone.
+     *
+     * @param tz the time zone.
+     */
+    public void setTz(String tz) {
+        this.tz = tz;
+    }
+
+    /**
+     * Returns the local (non-utc) time in human-friendly format.
+     *
+     * @return the local time in human-friendly format.
+     */
+    public String getDisplay() {
+        return display;
+    }
+
+    /**
+     * Sets the local time in human-friendly format.
+     *
+     * @param display the local time in human-friendly format.
+     */
+    public void setDisplay(String display) {
+        this.display = display;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:time\">");
+        if (utc != null) {
+            buf.append("<utc>").append(utc).append("</utc>");
+        }
+        if (tz != null) {
+            buf.append("<tz>").append(tz).append("</tz>");
+        }
+        if (display != null) {
+            buf.append("<display>").append(display).append("</display>");
+        }
+        buf.append("</query>");
+        return buf.toString();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/packet/VCard.java b/src/org/jivesoftware/smackx/packet/VCard.java
new file mode 100644
index 0000000..9766db8
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/VCard.java
@@ -0,0 +1,883 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import java.io.BufferedInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
+import java.net.URL;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Map.Entry;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.util.StringUtils;
+
+/**
+ * A VCard class for use with the
+ * <a href="http://www.jivesoftware.org/smack/" target="_blank">SMACK jabber library</a>.<p>
+ * <p/>
+ * You should refer to the
+ * <a href="http://www.jabber.org/jeps/jep-0054.html" target="_blank">JEP-54 documentation</a>.<p>
+ * <p/>
+ * Please note that this class is incomplete but it does provide the most commonly found
+ * information in vCards. Also remember that VCard transfer is not a standard, and the protocol
+ * may change or be replaced.<p>
+ * <p/>
+ * <b>Usage:</b>
+ * <pre>
+ * <p/>
+ * // To save VCard:
+ * <p/>
+ * VCard vCard = new VCard();
+ * vCard.setFirstName("kir");
+ * vCard.setLastName("max");
+ * vCard.setEmailHome("foo@fee.bar");
+ * vCard.setJabberId("jabber@id.org");
+ * vCard.setOrganization("Jetbrains, s.r.o");
+ * vCard.setNickName("KIR");
+ * <p/>
+ * vCard.setField("TITLE", "Mr");
+ * vCard.setAddressFieldHome("STREET", "Some street");
+ * vCard.setAddressFieldWork("CTRY", "US");
+ * vCard.setPhoneWork("FAX", "3443233");
+ * <p/>
+ * vCard.save(connection);
+ * <p/>
+ * // To load VCard:
+ * <p/>
+ * VCard vCard = new VCard();
+ * vCard.load(conn); // load own VCard
+ * vCard.load(conn, "joe@foo.bar"); // load someone's VCard
+ * </pre>
+ *
+ * @author Kirill Maximov (kir@maxkir.com)
+ */
+public class VCard extends IQ {
+
+    /**
+     * Phone types:
+     * VOICE?, FAX?, PAGER?, MSG?, CELL?, VIDEO?, BBS?, MODEM?, ISDN?, PCS?, PREF?
+     */
+    private Map<String, String> homePhones = new HashMap<String, String>();
+    private Map<String, String> workPhones = new HashMap<String, String>();
+
+
+    /**
+     * Address types:
+     * POSTAL?, PARCEL?, (DOM | INTL)?, PREF?, POBOX?, EXTADR?, STREET?, LOCALITY?,
+     * REGION?, PCODE?, CTRY?
+     */
+    private Map<String, String> homeAddr = new HashMap<String, String>();
+    private Map<String, String> workAddr = new HashMap<String, String>();
+
+    private String firstName;
+    private String lastName;
+    private String middleName;
+
+    private String emailHome;
+    private String emailWork;
+
+    private String organization;
+    private String organizationUnit;
+
+    private String photoMimeType;
+    private String photoBinval;
+
+    /**
+     * Such as DESC ROLE GEO etc.. see JEP-0054
+     */
+    private Map<String, String> otherSimpleFields = new HashMap<String, String>();
+
+    // fields that, as they are should not be escaped before forwarding to the server
+    private Map<String, String> otherUnescapableFields = new HashMap<String, String>();
+
+    public VCard() {
+    }
+
+    /**
+     * Set generic VCard field.
+     *
+     * @param field value of field. Possible values: NICKNAME, PHOTO, BDAY, JABBERID, MAILER, TZ,
+     *              GEO, TITLE, ROLE, LOGO, NOTE, PRODID, REV, SORT-STRING, SOUND, UID, URL, DESC.
+     */
+    public String getField(String field) {
+        return otherSimpleFields.get(field);
+    }
+
+    /**
+     * Set generic VCard field.
+     *
+     * @param value value of field
+     * @param field field to set. See {@link #getField(String)}
+     * @see #getField(String)
+     */
+    public void setField(String field, String value) {
+        setField(field, value, false);
+    }
+
+    /**
+     * Set generic, unescapable VCard field. If unescabale is set to true, XML maybe a part of the
+     * value.
+     *
+     * @param value         value of field
+     * @param field         field to set. See {@link #getField(String)}
+     * @param isUnescapable True if the value should not be escaped, and false if it should.
+     */
+    public void setField(String field, String value, boolean isUnescapable) {
+        if (!isUnescapable) {
+            otherSimpleFields.put(field, value);
+        }
+        else {
+            otherUnescapableFields.put(field, value);
+        }
+    }
+
+    public String getFirstName() {
+        return firstName;
+    }
+
+    public void setFirstName(String firstName) {
+        this.firstName = firstName;
+        // Update FN field
+        updateFN();
+    }
+
+    public String getLastName() {
+        return lastName;
+    }
+
+    public void setLastName(String lastName) {
+        this.lastName = lastName;
+        // Update FN field
+        updateFN();
+    }
+
+    public String getMiddleName() {
+        return middleName;
+    }
+
+    public void setMiddleName(String middleName) {
+        this.middleName = middleName;
+        // Update FN field
+        updateFN();
+    }
+
+    public String getNickName() {
+        return otherSimpleFields.get("NICKNAME");
+    }
+
+    public void setNickName(String nickName) {
+        otherSimpleFields.put("NICKNAME", nickName);
+    }
+
+    public String getEmailHome() {
+        return emailHome;
+    }
+
+    public void setEmailHome(String email) {
+        this.emailHome = email;
+    }
+
+    public String getEmailWork() {
+        return emailWork;
+    }
+
+    public void setEmailWork(String emailWork) {
+        this.emailWork = emailWork;
+    }
+
+    public String getJabberId() {
+        return otherSimpleFields.get("JABBERID");
+    }
+
+    public void setJabberId(String jabberId) {
+        otherSimpleFields.put("JABBERID", jabberId);
+    }
+
+    public String getOrganization() {
+        return organization;
+    }
+
+    public void setOrganization(String organization) {
+        this.organization = organization;
+    }
+
+    public String getOrganizationUnit() {
+        return organizationUnit;
+    }
+
+    public void setOrganizationUnit(String organizationUnit) {
+        this.organizationUnit = organizationUnit;
+    }
+
+    /**
+     * Get home address field
+     *
+     * @param addrField one of POSTAL, PARCEL, (DOM | INTL), PREF, POBOX, EXTADR, STREET,
+     *                  LOCALITY, REGION, PCODE, CTRY
+     */
+    public String getAddressFieldHome(String addrField) {
+        return homeAddr.get(addrField);
+    }
+
+    /**
+     * Set home address field
+     *
+     * @param addrField one of POSTAL, PARCEL, (DOM | INTL), PREF, POBOX, EXTADR, STREET,
+     *                  LOCALITY, REGION, PCODE, CTRY
+     */
+    public void setAddressFieldHome(String addrField, String value) {
+        homeAddr.put(addrField, value);
+    }
+
+    /**
+     * Get work address field
+     *
+     * @param addrField one of POSTAL, PARCEL, (DOM | INTL), PREF, POBOX, EXTADR, STREET,
+     *                  LOCALITY, REGION, PCODE, CTRY
+     */
+    public String getAddressFieldWork(String addrField) {
+        return workAddr.get(addrField);
+    }
+
+    /**
+     * Set work address field
+     *
+     * @param addrField one of POSTAL, PARCEL, (DOM | INTL), PREF, POBOX, EXTADR, STREET,
+     *                  LOCALITY, REGION, PCODE, CTRY
+     */
+    public void setAddressFieldWork(String addrField, String value) {
+        workAddr.put(addrField, value);
+    }
+
+
+    /**
+     * Set home phone number
+     *
+     * @param phoneType one of VOICE, FAX, PAGER, MSG, CELL, VIDEO, BBS, MODEM, ISDN, PCS, PREF
+     * @param phoneNum  phone number
+     */
+    public void setPhoneHome(String phoneType, String phoneNum) {
+        homePhones.put(phoneType, phoneNum);
+    }
+
+    /**
+     * Get home phone number
+     *
+     * @param phoneType one of VOICE, FAX, PAGER, MSG, CELL, VIDEO, BBS, MODEM, ISDN, PCS, PREF
+     */
+    public String getPhoneHome(String phoneType) {
+        return homePhones.get(phoneType);
+    }
+
+    /**
+     * Set work phone number
+     *
+     * @param phoneType one of VOICE, FAX, PAGER, MSG, CELL, VIDEO, BBS, MODEM, ISDN, PCS, PREF
+     * @param phoneNum  phone number
+     */
+    public void setPhoneWork(String phoneType, String phoneNum) {
+        workPhones.put(phoneType, phoneNum);
+    }
+
+    /**
+     * Get work phone number
+     *
+     * @param phoneType one of VOICE, FAX, PAGER, MSG, CELL, VIDEO, BBS, MODEM, ISDN, PCS, PREF
+     */
+    public String getPhoneWork(String phoneType) {
+        return workPhones.get(phoneType);
+    }
+
+    /**
+     * Set the avatar for the VCard by specifying the url to the image.
+     *
+     * @param avatarURL the url to the image(png,jpeg,gif,bmp)
+     */
+    public void setAvatar(URL avatarURL) {
+        byte[] bytes = new byte[0];
+        try {
+            bytes = getBytes(avatarURL);
+        }
+        catch (IOException e) {
+            e.printStackTrace();
+        }
+
+        setAvatar(bytes);
+    }
+
+    /**
+     * Removes the avatar from the vCard
+     *
+     *  This is done by setting the PHOTO value to the empty string as defined in XEP-0153
+     */
+    public void removeAvatar() {
+        // Remove avatar (if any)
+        photoBinval = null;
+        photoMimeType = null;
+    }
+
+    /**
+     * Specify the bytes of the JPEG for the avatar to use.
+     * If bytes is null, then the avatar will be removed.
+     * 'image/jpeg' will be used as MIME type.
+     *
+     * @param bytes the bytes of the avatar, or null to remove the avatar data
+     */
+    public void setAvatar(byte[] bytes) {
+        setAvatar(bytes, "image/jpeg");
+    }
+
+    /**
+     * Specify the bytes for the avatar to use as well as the mime type.
+     *
+     * @param bytes the bytes of the avatar.
+     * @param mimeType the mime type of the avatar.
+     */
+    public void setAvatar(byte[] bytes, String mimeType) {
+        // If bytes is null, remove the avatar
+        if (bytes == null) {
+            removeAvatar();
+            return;
+        }
+
+        // Otherwise, add to mappings.
+        String encodedImage = StringUtils.encodeBase64(bytes);
+
+        setAvatar(encodedImage, mimeType);
+    }
+
+    /**
+     * Specify the Avatar used for this vCard.
+     *
+     * @param encodedImage the Base64 encoded image as String
+     * @param mimeType the MIME type of the image
+     */
+    public void setAvatar(String encodedImage, String mimeType) {
+        photoBinval = encodedImage;
+        photoMimeType = mimeType;
+    }
+
+    /**
+     * Return the byte representation of the avatar(if one exists), otherwise returns null if
+     * no avatar could be found.
+     * <b>Example 1</b>
+     * <pre>
+     * // Load Avatar from VCard
+     * byte[] avatarBytes = vCard.getAvatar();
+     * <p/>
+     * // To create an ImageIcon for Swing applications
+     * ImageIcon icon = new ImageIcon(avatar);
+     * <p/>
+     * // To create just an image object from the bytes
+     * ByteArrayInputStream bais = new ByteArrayInputStream(avatar);
+     * try {
+     *   Image image = ImageIO.read(bais);
+     *  }
+     *  catch (IOException e) {
+     *    e.printStackTrace();
+     * }
+     * </pre>
+     *
+     * @return byte representation of avatar.
+     */
+    public byte[] getAvatar() {
+        if (photoBinval == null) {
+            return null;
+        }
+        return StringUtils.decodeBase64(photoBinval);
+    }
+
+    /**
+     * Returns the MIME Type of the avatar or null if none is set
+     *
+     * @return the MIME Type of the avatar or null
+     */
+    public String getAvatarMimeType() {
+        return photoMimeType;
+    }
+
+    /**
+     * Common code for getting the bytes of a url.
+     *
+     * @param url the url to read.
+     */
+    public static byte[] getBytes(URL url) throws IOException {
+        final String path = url.getPath();
+        final File file = new File(path);
+        if (file.exists()) {
+            return getFileBytes(file);
+        }
+
+        return null;
+    }
+
+    private static byte[] getFileBytes(File file) throws IOException {
+        BufferedInputStream bis = null;
+        try {
+            bis = new BufferedInputStream(new FileInputStream(file));
+            int bytes = (int) file.length();
+            byte[] buffer = new byte[bytes];
+            int readBytes = bis.read(buffer);
+            if (readBytes != buffer.length) {
+                throw new IOException("Entire file not read");
+            }
+            return buffer;
+        }
+        finally {
+            if (bis != null) {
+                bis.close();
+            }
+        }
+    }
+
+    /**
+     * Returns the SHA-1 Hash of the Avatar image.
+     *
+     * @return the SHA-1 Hash of the Avatar image.
+     */
+    public String getAvatarHash() {
+        byte[] bytes = getAvatar();
+        if (bytes == null) {
+            return null;
+        }
+
+        MessageDigest digest;
+        try {
+            digest = MessageDigest.getInstance("SHA-1");
+        }
+        catch (NoSuchAlgorithmException e) {
+            e.printStackTrace();
+            return null;
+        }
+
+        digest.update(bytes);
+        return StringUtils.encodeHex(digest.digest());
+    }
+
+    private void updateFN() {
+        StringBuilder sb = new StringBuilder();
+        if (firstName != null) {
+            sb.append(StringUtils.escapeForXML(firstName)).append(' ');
+        }
+        if (middleName != null) {
+            sb.append(StringUtils.escapeForXML(middleName)).append(' ');
+        }
+        if (lastName != null) {
+            sb.append(StringUtils.escapeForXML(lastName));
+        }
+        setField("FN", sb.toString());
+    }
+
+    /**
+     * Save this vCard for the user connected by 'connection'. Connection should be authenticated
+     * and not anonymous.<p>
+     * <p/>
+     * NOTE: the method is asynchronous and does not wait for the returned value.
+     *
+     * @param connection the Connection to use.
+     * @throws XMPPException thrown if there was an issue setting the VCard in the server.
+     */
+    public void save(Connection connection) throws XMPPException {
+        checkAuthenticated(connection, true);
+
+        setType(IQ.Type.SET);
+        setFrom(connection.getUser());
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(getPacketID()));
+        connection.sendPacket(this);
+
+        Packet response = collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Load VCard information for a connected user. Connection should be authenticated
+     * and not anonymous.
+     */
+    public void load(Connection connection) throws XMPPException {
+        checkAuthenticated(connection, true);
+
+        setFrom(connection.getUser());
+        doLoad(connection, connection.getUser());
+    }
+
+    /**
+     * Load VCard information for a given user. Connection should be authenticated and not anonymous.
+     */
+    public void load(Connection connection, String user) throws XMPPException {
+        checkAuthenticated(connection, false);
+
+        setTo(user);
+        doLoad(connection, user);
+    }
+
+    private void doLoad(Connection connection, String user) throws XMPPException {
+        setType(Type.GET);
+        PacketCollector collector = connection.createPacketCollector(
+                new PacketIDFilter(getPacketID()));
+        connection.sendPacket(this);
+
+        VCard result = null;
+        try {
+            result = (VCard) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+            if (result == null) {
+                String errorMessage = "Timeout getting VCard information";
+                throw new XMPPException(errorMessage, new XMPPError(
+                        XMPPError.Condition.request_timeout, errorMessage));
+            }
+            if (result.getError() != null) {
+                throw new XMPPException(result.getError());
+            }
+        }
+        catch (ClassCastException e) {
+            System.out.println("No VCard for " + user);
+        }
+
+        copyFieldsFrom(result);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder sb = new StringBuilder();
+        new VCardWriter(sb).write();
+        return sb.toString();
+    }
+
+    private void copyFieldsFrom(VCard from) {
+        Field[] fields = VCard.class.getDeclaredFields();
+        for (Field field : fields) {
+            if (field.getDeclaringClass() == VCard.class &&
+                    !Modifier.isFinal(field.getModifiers())) {
+                try {
+                    field.setAccessible(true);
+                    field.set(this, field.get(from));
+                }
+                catch (IllegalAccessException e) {
+                    throw new RuntimeException("This cannot happen:" + field, e);
+                }
+            }
+        }
+    }
+
+    private void checkAuthenticated(Connection connection, boolean checkForAnonymous) {
+        if (connection == null) {
+            throw new IllegalArgumentException("No connection was provided");
+        }
+        if (!connection.isAuthenticated()) {
+            throw new IllegalArgumentException("Connection is not authenticated");
+        }
+        if (checkForAnonymous && connection.isAnonymous()) {
+            throw new IllegalArgumentException("Connection cannot be anonymous");
+        }
+    }
+
+    private boolean hasContent() {
+        //noinspection OverlyComplexBooleanExpression
+        return hasNameField()
+                || hasOrganizationFields()
+                || emailHome != null
+                || emailWork != null
+                || otherSimpleFields.size() > 0
+                || otherUnescapableFields.size() > 0
+                || homeAddr.size() > 0
+                || homePhones.size() > 0
+                || workAddr.size() > 0
+                || workPhones.size() > 0
+                || photoBinval != null
+                ;
+    }
+
+    private boolean hasNameField() {
+        return firstName != null || lastName != null || middleName != null;
+    }
+
+    private boolean hasOrganizationFields() {
+        return organization != null || organizationUnit != null;
+    }
+
+    // Used in tests:
+
+    public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+
+        final VCard vCard = (VCard) o;
+
+        if (emailHome != null ? !emailHome.equals(vCard.emailHome) : vCard.emailHome != null) {
+            return false;
+        }
+        if (emailWork != null ? !emailWork.equals(vCard.emailWork) : vCard.emailWork != null) {
+            return false;
+        }
+        if (firstName != null ? !firstName.equals(vCard.firstName) : vCard.firstName != null) {
+            return false;
+        }
+        if (!homeAddr.equals(vCard.homeAddr)) {
+            return false;
+        }
+        if (!homePhones.equals(vCard.homePhones)) {
+            return false;
+        }
+        if (lastName != null ? !lastName.equals(vCard.lastName) : vCard.lastName != null) {
+            return false;
+        }
+        if (middleName != null ? !middleName.equals(vCard.middleName) : vCard.middleName != null) {
+            return false;
+        }
+        if (organization != null ?
+                !organization.equals(vCard.organization) : vCard.organization != null) {
+            return false;
+        }
+        if (organizationUnit != null ?
+                !organizationUnit.equals(vCard.organizationUnit) : vCard.organizationUnit != null) {
+            return false;
+        }
+        if (!otherSimpleFields.equals(vCard.otherSimpleFields)) {
+            return false;
+        }
+        if (!workAddr.equals(vCard.workAddr)) {
+            return false;
+        }
+        if (photoBinval != null ? !photoBinval.equals(vCard.photoBinval) : vCard.photoBinval != null) {
+            return false;
+        }
+
+        return workPhones.equals(vCard.workPhones);
+    }
+
+    public int hashCode() {
+        int result;
+        result = homePhones.hashCode();
+        result = 29 * result + workPhones.hashCode();
+        result = 29 * result + homeAddr.hashCode();
+        result = 29 * result + workAddr.hashCode();
+        result = 29 * result + (firstName != null ? firstName.hashCode() : 0);
+        result = 29 * result + (lastName != null ? lastName.hashCode() : 0);
+        result = 29 * result + (middleName != null ? middleName.hashCode() : 0);
+        result = 29 * result + (emailHome != null ? emailHome.hashCode() : 0);
+        result = 29 * result + (emailWork != null ? emailWork.hashCode() : 0);
+        result = 29 * result + (organization != null ? organization.hashCode() : 0);
+        result = 29 * result + (organizationUnit != null ? organizationUnit.hashCode() : 0);
+        result = 29 * result + otherSimpleFields.hashCode();
+        result = 29 * result + (photoBinval != null ? photoBinval.hashCode() : 0);
+        return result;
+    }
+
+    public String toString() {
+        return getChildElementXML();
+    }
+
+    //==============================================================
+
+    private class VCardWriter {
+
+        private final StringBuilder sb;
+
+        VCardWriter(StringBuilder sb) {
+            this.sb = sb;
+        }
+
+        public void write() {
+            appendTag("vCard", "xmlns", "vcard-temp", hasContent(), new ContentBuilder() {
+                public void addTagContent() {
+                    buildActualContent();
+                }
+            });
+        }
+
+        private void buildActualContent() {
+            if (hasNameField()) {
+                appendN();
+            }
+
+            appendOrganization();
+            appendGenericFields();
+            appendPhoto();
+
+            appendEmail(emailWork, "WORK");
+            appendEmail(emailHome, "HOME");
+
+            appendPhones(workPhones, "WORK");
+            appendPhones(homePhones, "HOME");
+
+            appendAddress(workAddr, "WORK");
+            appendAddress(homeAddr, "HOME");
+        }
+
+        private void appendPhoto() {
+            if (photoBinval == null)
+                return;
+
+            appendTag("PHOTO", true, new ContentBuilder() {
+                public void addTagContent() {
+                    appendTag("BINVAL", photoBinval); // No need to escape photoBinval, as it's already Base64 encoded
+                    appendTag("TYPE", StringUtils.escapeForXML(photoMimeType));
+                }
+            });
+        }
+        private void appendEmail(final String email, final String type) {
+            if (email != null) {
+                appendTag("EMAIL", true, new ContentBuilder() {
+                    public void addTagContent() {
+                        appendEmptyTag(type);
+                        appendEmptyTag("INTERNET");
+                        appendEmptyTag("PREF");
+                        appendTag("USERID", StringUtils.escapeForXML(email));
+                    }
+                });
+            }
+        }
+
+        private void appendPhones(Map<String, String> phones, final String code) {
+            Iterator<Map.Entry<String, String>> it = phones.entrySet().iterator();
+            while (it.hasNext()) {
+                final Map.Entry<String,String> entry = it.next();
+                appendTag("TEL", true, new ContentBuilder() {
+                    public void addTagContent() {
+                        appendEmptyTag(entry.getKey());
+                        appendEmptyTag(code);
+                        appendTag("NUMBER", StringUtils.escapeForXML(entry.getValue()));
+                    }
+                });
+            }
+        }
+
+        private void appendAddress(final Map<String, String> addr, final String code) {
+            if (addr.size() > 0) {
+                appendTag("ADR", true, new ContentBuilder() {
+                    public void addTagContent() {
+                        appendEmptyTag(code);
+
+                        Iterator<Map.Entry<String, String>> it = addr.entrySet().iterator();
+                        while (it.hasNext()) {
+                            final Entry<String, String> entry = it.next();
+                            appendTag(entry.getKey(), StringUtils.escapeForXML(entry.getValue()));
+                        }
+                    }
+                });
+            }
+        }
+
+        private void appendEmptyTag(Object tag) {
+            sb.append('<').append(tag).append("/>");
+        }
+
+        private void appendGenericFields() {
+            Iterator<Map.Entry<String, String>> it = otherSimpleFields.entrySet().iterator();
+            while (it.hasNext()) {
+                Map.Entry<String, String> entry = it.next();
+                appendTag(entry.getKey().toString(),
+                        StringUtils.escapeForXML(entry.getValue()));
+            }
+
+            it = otherUnescapableFields.entrySet().iterator();
+            while (it.hasNext()) {
+                Map.Entry<String, String> entry = it.next();
+                appendTag(entry.getKey().toString(),entry.getValue());
+            }
+        }
+
+        private void appendOrganization() {
+            if (hasOrganizationFields()) {
+                appendTag("ORG", true, new ContentBuilder() {
+                    public void addTagContent() {
+                        appendTag("ORGNAME", StringUtils.escapeForXML(organization));
+                        appendTag("ORGUNIT", StringUtils.escapeForXML(organizationUnit));
+                    }
+                });
+            }
+        }
+
+        private void appendN() {
+            appendTag("N", true, new ContentBuilder() {
+                public void addTagContent() {
+                    appendTag("FAMILY", StringUtils.escapeForXML(lastName));
+                    appendTag("GIVEN", StringUtils.escapeForXML(firstName));
+                    appendTag("MIDDLE", StringUtils.escapeForXML(middleName));
+                }
+            });
+        }
+
+        private void appendTag(String tag, String attr, String attrValue, boolean hasContent,
+                ContentBuilder builder) {
+            sb.append('<').append(tag);
+            if (attr != null) {
+                sb.append(' ').append(attr).append('=').append('\'').append(attrValue).append('\'');
+            }
+
+            if (hasContent) {
+                sb.append('>');
+                builder.addTagContent();
+                sb.append("</").append(tag).append(">\n");
+            }
+            else {
+                sb.append("/>\n");
+            }
+        }
+
+        private void appendTag(String tag, boolean hasContent, ContentBuilder builder) {
+            appendTag(tag, null, null, hasContent, builder);
+        }
+
+        private void appendTag(String tag, final String tagText) {
+            if (tagText == null) return;
+            final ContentBuilder contentBuilder = new ContentBuilder() {
+                public void addTagContent() {
+                    sb.append(tagText.trim());
+                }
+            };
+            appendTag(tag, true, contentBuilder);
+        }
+
+    }
+
+    //==============================================================
+
+    private interface ContentBuilder {
+
+        void addTagContent();
+    }
+
+    //==============================================================
+}
+
diff --git a/src/org/jivesoftware/smackx/packet/Version.java b/src/org/jivesoftware/smackx/packet/Version.java
new file mode 100644
index 0000000..41ee419
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/Version.java
@@ -0,0 +1,132 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+/**
+ * A Version IQ packet, which is used by XMPP clients to discover version information
+ * about the software running at another entity's JID.<p>
+ *
+ * An example to discover the version of the server:
+ * <pre>
+ * // Request the version from the server.
+ * Version versionRequest = new Version();
+ * timeRequest.setType(IQ.Type.GET);
+ * timeRequest.setTo("example.com");
+ *
+ * // Create a packet collector to listen for a response.
+ * PacketCollector collector = con.createPacketCollector(
+ *                new PacketIDFilter(versionRequest.getPacketID()));
+ *
+ * con.sendPacket(versionRequest);
+ *
+ * // Wait up to 5 seconds for a result.
+ * IQ result = (IQ)collector.nextResult(5000);
+ * if (result != null && result.getType() == IQ.Type.RESULT) {
+ *     Version versionResult = (Version)result;
+ *     // Do something with result...
+ * }</pre><p>
+ *
+ * @author Gaston Dombiak
+ */
+public class Version extends IQ {
+
+    private String name;
+    private String version;
+    private String os;
+
+    /**
+     * Returns the natural-language name of the software. This property will always be
+     * present in a result.
+     *
+     * @return the natural-language name of the software.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Sets the natural-language name of the software. This message should only be
+     * invoked when parsing the XML and setting the property to a Version instance.
+     *
+     * @param name the natural-language name of the software.
+     */
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    /**
+     * Returns the specific version of the software. This property will always be
+     * present in a result.
+     *
+     * @return the specific version of the software.
+     */
+    public String getVersion() {
+        return version;
+    }
+
+    /**
+     * Sets the specific version of the software. This message should only be
+     * invoked when parsing the XML and setting the property to a Version instance.
+     *
+     * @param version the specific version of the software.
+     */
+    public void setVersion(String version) {
+        this.version = version;
+    }
+
+    /**
+     * Returns the operating system of the queried entity. This property will always be
+     * present in a result.
+     *
+     * @return the operating system of the queried entity.
+     */
+    public String getOs() {
+        return os;
+    }
+
+    /**
+     * Sets the operating system of the queried entity. This message should only be
+     * invoked when parsing the XML and setting the property to a Version instance.
+     *
+     * @param os operating system of the queried entity.
+     */
+    public void setOs(String os) {
+        this.os = os;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:version\">");
+        if (name != null) {
+            buf.append("<name>").append(name).append("</name>");
+        }
+        if (version != null) {
+            buf.append("<version>").append(version).append("</version>");
+        }
+        if (os != null) {
+            buf.append("<os>").append(os).append("</os>");
+        }
+        buf.append("</query>");
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/packet/XHTMLExtension.java b/src/org/jivesoftware/smackx/packet/XHTMLExtension.java
new file mode 100644
index 0000000..ba5e676
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/XHTMLExtension.java
@@ -0,0 +1,126 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * An XHTML sub-packet, which is used by XMPP clients to exchange formatted text. The XHTML 
+ * extension is only a subset of XHTML 1.0.<p>
+ * 
+ * The following link summarizes the requirements of XHTML IM:
+ * <a href="http://www.jabber.org/jeps/jep-0071.html#sect-id2598018">Valid tags</a>.<p>
+ * 
+ * Warning: this is an non-standard protocol documented by
+ * <a href="http://www.jabber.org/jeps/jep-0071.html">JEP-71</a>. Because this is a
+ * non-standard protocol, it is subject to change.
+ *
+ * @author Gaston Dombiak
+ */
+public class XHTMLExtension implements PacketExtension {
+
+    private List<String> bodies = new ArrayList<String>();
+
+    /**
+    * Returns the XML element name of the extension sub-packet root element.
+    * Always returns "html"
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "html";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is always "http://jabber.org/protocol/xhtml-im"
+     *
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() {
+        return "http://jabber.org/protocol/xhtml-im";
+    }
+
+    /**
+     * Returns the XML representation of a XHTML extension according the specification.
+     * 
+     * Usually the XML representation will be inside of a Message XML representation like
+     * in the following example:
+     * <pre>
+     * &lt;message id="MlIpV-4" to="gato1@gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;subject&gt;Any subject you want&lt;/subject&gt;
+     *     &lt;body&gt;This message contains something interesting.&lt;/body&gt;
+     *     &lt;html xmlns="http://jabber.org/protocol/xhtml-im"&gt;
+     *         &lt;body&gt;&lt;p style='font-size:large'&gt;This message contains something &lt;em&gt;interesting&lt;/em&gt;.&lt;/p&gt;&lt;/body&gt;
+     *     &lt;/html&gt;
+     * &lt;/message&gt;
+     * </pre>
+     * 
+     */
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append(
+            "\">");
+        // Loop through all the bodies and append them to the string buffer
+        for (Iterator<String> i = getBodies(); i.hasNext();) {
+            buf.append(i.next());
+        }
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Returns an Iterator for the bodies in the packet.
+     *
+     * @return an Iterator for the bodies in the packet.
+     */
+    public Iterator<String> getBodies() {
+        synchronized (bodies) {
+            return Collections.unmodifiableList(new ArrayList<String>(bodies)).iterator();
+        }
+    }
+
+    /**
+     * Adds a body to the packet.
+     *
+     * @param body the body to add.
+     */
+    public void addBody(String body) {
+        synchronized (bodies) {
+            bodies.add(body);
+        }
+    }
+
+    /**
+     * Returns a count of the bodies in the XHTML packet.
+     *
+     * @return the number of bodies in the XHTML packet.
+     */
+    public int getBodiesCount() {
+        return bodies.size();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/packet/package.html b/src/org/jivesoftware/smackx/packet/package.html
new file mode 100644
index 0000000..490d1d7
--- /dev/null
+++ b/src/org/jivesoftware/smackx/packet/package.html
@@ -0,0 +1 @@
+<body>XML packets that are part of the XMPP extension protocols.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/ping/PingFailedListener.java b/src/org/jivesoftware/smackx/ping/PingFailedListener.java
new file mode 100644
index 0000000..4cda33b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/PingFailedListener.java
@@ -0,0 +1,21 @@
+/**
+ * Copyright 2012 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping;
+
+public interface PingFailedListener {
+    void pingFailed();
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/ping/PingManager.java b/src/org/jivesoftware/smackx/ping/PingManager.java
new file mode 100644
index 0000000..6b4b48c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/PingManager.java
@@ -0,0 +1,343 @@
+/**
+ * Copyright 2012-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping;
+
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+import java.util.WeakHashMap;
+import java.util.concurrent.ScheduledExecutorService;
+import java.util.concurrent.ScheduledFuture;
+import java.util.concurrent.ScheduledThreadPoolExecutor;
+import java.util.concurrent.TimeUnit;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.ConnectionListener;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.ping.packet.Ping;
+import org.jivesoftware.smackx.ping.packet.Pong;
+
+/**
+ * Implements the XMPP Ping as defined by XEP-0199. This protocol offers an
+ * alternative to the traditional 'white space ping' approach of determining the
+ * availability of an entity. The XMPP Ping protocol allows ping messages to be
+ * send in a more XML-friendly approach, which can be used over more than one
+ * hop in the communication path.
+ * 
+ * @author Florian Schmaus
+ * @see <a href="http://www.xmpp.org/extensions/xep-0199.html">XEP-0199:XMPP
+ *      Ping</a>
+ */
+public class PingManager {
+    
+    public static final String NAMESPACE = "urn:xmpp:ping";
+    public static final String ELEMENT = "ping";
+    
+
+    private static Map<Connection, PingManager> instances =
+            Collections.synchronizedMap(new WeakHashMap<Connection, PingManager>());
+    
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new PingManager(connection);
+            }
+        });
+    }
+    
+    private ScheduledExecutorService periodicPingExecutorService;
+    private Connection connection;
+    private int pingInterval = SmackConfiguration.getDefaultPingInterval();
+    private Set<PingFailedListener> pingFailedListeners = Collections
+            .synchronizedSet(new HashSet<PingFailedListener>());
+    private ScheduledFuture<?> periodicPingTask;
+    protected volatile long lastSuccessfulPingByTask = -1;
+
+    
+    // Ping Flood protection
+    private long pingMinDelta = 100;
+    private long lastPingStamp = 0; // timestamp of the last received ping
+    
+    // Timestamp of the last pong received, either from the server or another entity
+    // Note, no need to synchronize this value, it will only increase over time
+    private long lastSuccessfulManualPing = -1;
+    
+    private PingManager(Connection connection) {
+        ServiceDiscoveryManager sdm = ServiceDiscoveryManager.getInstanceFor(connection);
+        sdm.addFeature(NAMESPACE);
+        this.connection = connection;
+        init();
+    }
+    
+    private void init() {
+        periodicPingExecutorService = new ScheduledThreadPoolExecutor(1);
+        PacketFilter pingPacketFilter = new PacketTypeFilter(Ping.class);
+        connection.addPacketListener(new PacketListener() {
+            /**
+             * Sends a Pong for every Ping
+             */
+            public void processPacket(Packet packet) {
+                if (pingMinDelta > 0) {
+                    // Ping flood protection enabled
+                    long currentMillies = System.currentTimeMillis();
+                    long delta = currentMillies - lastPingStamp;
+                    lastPingStamp = currentMillies;
+                    if (delta < pingMinDelta) {
+                        return;
+                    }
+                }
+                Pong pong = new Pong((Ping)packet);
+                connection.sendPacket(pong);
+            }
+        }
+        , pingPacketFilter);
+        connection.addConnectionListener(new ConnectionListener() {
+
+            @Override
+            public void connectionClosed() {
+                maybeStopPingServerTask();
+            }
+
+            @Override
+            public void connectionClosedOnError(Exception arg0) {
+                maybeStopPingServerTask();
+            }
+
+            @Override
+            public void reconnectionSuccessful() {
+                maybeSchedulePingServerTask();
+            }
+
+            @Override
+            public void reconnectingIn(int seconds) {
+            }
+
+            @Override
+            public void reconnectionFailed(Exception e) {
+            }
+        });
+        instances.put(connection, this);
+        maybeSchedulePingServerTask();
+    }
+
+    public static PingManager getInstanceFor(Connection connection) {
+        PingManager pingManager = instances.get(connection);
+        
+        if (pingManager == null) {
+            pingManager = new PingManager(connection);
+        }
+
+        return pingManager;
+    }
+
+    public void setPingIntervall(int pingIntervall) {
+        this.pingInterval = pingIntervall;
+    }
+
+    public int getPingIntervall() {
+        return pingInterval;
+    }
+    
+    public void registerPingFailedListener(PingFailedListener listener) {
+        pingFailedListeners.add(listener);
+    }
+    
+    public void unregisterPingFailedListener(PingFailedListener listener) {
+        pingFailedListeners.remove(listener);
+    }
+    
+    public void disablePingFloodProtection() {
+        setPingMinimumInterval(-1);
+    }
+    
+    public void setPingMinimumInterval(long ms) {
+        this.pingMinDelta = ms;
+    }
+    
+    public long getPingMinimumInterval() {
+        return this.pingMinDelta;
+    }
+    
+    /**
+     * Pings the given jid and returns the IQ response which is either of 
+     * IQ.Type.ERROR or IQ.Type.RESULT. If we are not connected or if there was
+     * no reply, null is returned.
+     * 
+     * You should use isPingSupported(jid) to determine if XMPP Ping is 
+     * supported by the user.
+     * 
+     * @param jid
+     * @param pingTimeout
+     * @return
+     */
+    public IQ ping(String jid, long pingTimeout) {
+        // Make sure we actually connected to the server
+        if (!connection.isAuthenticated())
+            return null;
+        
+        Ping ping = new Ping(connection.getUser(), jid);
+        
+        PacketCollector collector =
+                connection.createPacketCollector(new PacketIDFilter(ping.getPacketID()));
+        
+        connection.sendPacket(ping);
+        
+        IQ result = (IQ) collector.nextResult(pingTimeout);
+        
+        collector.cancel();
+        return result;
+    }
+    
+    /**
+     * Pings the given jid and returns the IQ response with the default
+     * packet reply timeout
+     * 
+     * @param jid
+     * @return
+     */
+    public IQ ping(String jid) {
+        return ping(jid, SmackConfiguration.getPacketReplyTimeout());
+    }
+    
+    /**
+     * Pings the given Entity.
+     * 
+     * Note that XEP-199 shows that if we receive a error response
+     * service-unavailable there is no way to determine if the response was send
+     * by the entity (e.g. a user JID) or from a server in between. This is
+     * intended behavior to avoid presence leaks.
+     * 
+     * Always use isPingSupported(jid) to determine if XMPP Ping is supported
+     * by the entity.
+     * 
+     * @param jid
+     * @return True if a pong was received, otherwise false
+     */
+    public boolean pingEntity(String jid, long pingTimeout) {
+        IQ result = ping(jid, pingTimeout);
+
+        if (result == null || result.getType() == IQ.Type.ERROR) {
+            return false;
+        }
+        pongReceived();
+        return true;
+    }
+    
+    public boolean pingEntity(String jid) {
+        return pingEntity(jid, SmackConfiguration.getPacketReplyTimeout());
+    }
+    
+    /**
+     * Pings the user's server. Will notify the registered 
+     * pingFailedListeners in case of error.
+     * 
+     * If we receive as response, we can be sure that it came from the server.
+     * 
+     * @return true if successful, otherwise false
+     */
+    public boolean pingMyServer(long pingTimeout) {
+        IQ result = ping(connection.getServiceName(), pingTimeout);
+
+        if (result == null) {
+            for (PingFailedListener l : pingFailedListeners) {
+                l.pingFailed();
+            }
+            return false;
+        }
+        // Maybe not really a pong, but an answer is an answer
+        pongReceived();
+        return true;
+    }
+    
+    /**
+     * Pings the user's server with the PacketReplyTimeout as defined
+     * in SmackConfiguration.
+     * 
+     * @return true if successful, otherwise false
+     */
+    public boolean pingMyServer() {
+        return pingMyServer(SmackConfiguration.getPacketReplyTimeout());
+    }
+    
+    /**
+     * Returns true if XMPP Ping is supported by a given JID
+     * 
+     * @param jid
+     * @return
+     */
+    public boolean isPingSupported(String jid) {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(jid);
+            return result.containsFeature(NAMESPACE);
+        }
+        catch (XMPPException e) {
+            return false;
+        }
+    }
+    
+    /**
+     * Returns the time of the last successful Ping Pong with the 
+     * users server. If there was no successful Ping (e.g. because this
+     * feature is disabled) -1 will be returned.
+     *  
+     * @return
+     */
+    public long getLastSuccessfulPing() {
+        return Math.max(lastSuccessfulPingByTask, lastSuccessfulManualPing);
+    }
+    
+    protected Set<PingFailedListener> getPingFailedListeners() {
+        return pingFailedListeners;
+    }
+
+    /**
+     * Cancels any existing periodic ping task if there is one and schedules a new ping task if pingInterval is greater
+     * then zero.
+     * 
+     */
+    protected synchronized void maybeSchedulePingServerTask() {
+        maybeStopPingServerTask();
+        if (pingInterval > 0) {
+            periodicPingTask = periodicPingExecutorService.schedule(new ServerPingTask(connection), pingInterval,
+                    TimeUnit.SECONDS);
+        }
+    }
+
+    private void maybeStopPingServerTask() {
+        if (periodicPingTask != null) {
+            periodicPingTask.cancel(true);
+            periodicPingTask = null;
+        }
+    }
+
+    private void pongReceived() {
+        lastSuccessfulManualPing = System.currentTimeMillis();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/ping/ServerPingTask.java b/src/org/jivesoftware/smackx/ping/ServerPingTask.java
new file mode 100644
index 0000000..0901b8f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/ServerPingTask.java
@@ -0,0 +1,77 @@
+/**
+ * Copyright 2012-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping;
+
+import java.lang.ref.WeakReference;
+import java.util.Set;
+
+import org.jivesoftware.smack.Connection;
+
+class ServerPingTask implements Runnable {
+
+    // This has to be a weak reference because IIRC all threads are roots
+    // for objects and we have a new thread here that should hold a strong
+    // reference to connection so that it can be GCed.
+    private WeakReference<Connection> weakConnection;
+
+    private int delta = 1000; // 1 seconds
+    private int tries = 3; // 3 tries
+
+    protected ServerPingTask(Connection connection) {
+        this.weakConnection = new WeakReference<Connection>(connection);
+    }
+
+    public void run() {
+        Connection connection = weakConnection.get();
+        if (connection == null) {
+            // connection has been collected by GC
+            // which means we can stop the thread by breaking the loop
+            return;
+        }
+        if (connection.isAuthenticated()) {
+            PingManager pingManager = PingManager.getInstanceFor(connection);
+            boolean res = false;
+
+            for (int i = 0; i < tries; i++) {
+                if (i != 0) {
+                    try {
+                        Thread.sleep(delta);
+                    } catch (InterruptedException e) {
+                        // We received an interrupt
+                        // This only happens if we should stop pinging
+                        return;
+                    }
+                }
+                res = pingManager.pingMyServer();
+                // stop when we receive a pong back
+                if (res) {
+                    pingManager.lastSuccessfulPingByTask = System.currentTimeMillis();
+                    break;
+                }
+            }
+            if (!res) {
+                Set<PingFailedListener> pingFailedListeners = pingManager.getPingFailedListeners();
+                for (PingFailedListener l : pingFailedListeners) {
+                    l.pingFailed();
+                }
+            } else {
+                // Ping was successful, wind-up the periodic task again
+                pingManager.maybeSchedulePingServerTask();
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/ping/packet/Ping.java b/src/org/jivesoftware/smackx/ping/packet/Ping.java
new file mode 100644
index 0000000..fc5bbdf
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/packet/Ping.java
@@ -0,0 +1,38 @@
+/**
+ * Copyright 2012 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.ping.PingManager;
+
+public class Ping extends IQ {
+    
+    public Ping() {
+    }
+    
+    public Ping(String from, String to) {
+        setTo(to);
+        setFrom(from);
+        setType(IQ.Type.GET);
+        setPacketID(getPacketID());
+    }
+    
+    public String getChildElementXML() {
+        return "<" + PingManager.ELEMENT + " xmlns=\'" + PingManager.NAMESPACE + "\' />";
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/ping/packet/Pong.java b/src/org/jivesoftware/smackx/ping/packet/Pong.java
new file mode 100644
index 0000000..9300db0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/packet/Pong.java
@@ -0,0 +1,45 @@
+/**
+ * Copyright 2012 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+public class Pong extends IQ {
+    
+    /**
+     * Composes a Pong packet from a received ping packet. This basically swaps
+     * the 'from' and 'to' attributes. And sets the IQ type to result.
+     * 
+     * @param ping
+     */
+    public Pong(Ping ping) {
+        setType(IQ.Type.RESULT);
+        setFrom(ping.getTo());
+        setTo(ping.getFrom());
+        setPacketID(ping.getPacketID());
+    }
+    
+    /*
+     * Returns the child element of the Pong reply, which is non-existent. This
+     * is why we return 'null' here. See e.g. Example 11 from
+     * http://xmpp.org/extensions/xep-0199.html#e2e
+     */
+    public String getChildElementXML() {
+        return null;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/ping/provider/PingProvider.java b/src/org/jivesoftware/smackx/ping/provider/PingProvider.java
new file mode 100644
index 0000000..ebe7669
--- /dev/null
+++ b/src/org/jivesoftware/smackx/ping/provider/PingProvider.java
@@ -0,0 +1,32 @@
+/**
+ * Copyright 2012 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.ping.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.ping.packet.Ping;
+import org.xmlpull.v1.XmlPullParser;
+
+public class PingProvider implements IQProvider {
+    
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        // No need to use the ping constructor with arguments. IQ will already
+        // have filled out all relevant fields ('from', 'to', 'id').
+        return new Ping();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/AdHocCommandDataProvider.java b/src/org/jivesoftware/smackx/provider/AdHocCommandDataProvider.java
new file mode 100755
index 0000000..63d24ec
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/AdHocCommandDataProvider.java
@@ -0,0 +1,155 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2005-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.XMPPError;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.commands.AdHocCommand;
+import org.jivesoftware.smackx.commands.AdHocCommand.Action;
+import org.jivesoftware.smackx.commands.AdHocCommandNote;
+import org.jivesoftware.smackx.packet.AdHocCommandData;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The AdHocCommandDataProvider parses AdHocCommandData packets.
+ * 
+ * @author Gabriel Guardincerri
+ */
+public class AdHocCommandDataProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        AdHocCommandData adHocCommandData = new AdHocCommandData();
+        DataFormProvider dataFormProvider = new DataFormProvider();
+
+        int eventType;
+        String elementName;
+        String namespace;
+        adHocCommandData.setSessionID(parser.getAttributeValue("", "sessionid"));
+        adHocCommandData.setNode(parser.getAttributeValue("", "node"));
+
+        // Status
+        String status = parser.getAttributeValue("", "status");
+        if (AdHocCommand.Status.executing.toString().equalsIgnoreCase(status)) {
+            adHocCommandData.setStatus(AdHocCommand.Status.executing);
+        }
+        else if (AdHocCommand.Status.completed.toString().equalsIgnoreCase(status)) {
+            adHocCommandData.setStatus(AdHocCommand.Status.completed);
+        }
+        else if (AdHocCommand.Status.canceled.toString().equalsIgnoreCase(status)) {
+            adHocCommandData.setStatus(AdHocCommand.Status.canceled);
+        }
+
+        // Action
+        String action = parser.getAttributeValue("", "action");
+        if (action != null) {
+            Action realAction = AdHocCommand.Action.valueOf(action);
+            if (realAction == null || realAction.equals(Action.unknown)) {
+                adHocCommandData.setAction(Action.unknown);
+            }
+            else {
+                adHocCommandData.setAction(realAction);
+            }
+        }
+        while (!done) {
+            eventType = parser.next();
+            elementName = parser.getName();
+            namespace = parser.getNamespace();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("actions")) {
+                    String execute = parser.getAttributeValue("", "execute");
+                    if (execute != null) {
+                        adHocCommandData.setExecuteAction(AdHocCommand.Action.valueOf(execute));
+                    }
+                }
+                else if (parser.getName().equals("next")) {
+                    adHocCommandData.addAction(AdHocCommand.Action.next);
+                }
+                else if (parser.getName().equals("complete")) {
+                    adHocCommandData.addAction(AdHocCommand.Action.complete);
+                }
+                else if (parser.getName().equals("prev")) {
+                    adHocCommandData.addAction(AdHocCommand.Action.prev);
+                }
+                else if (elementName.equals("x") && namespace.equals("jabber:x:data")) {
+                    adHocCommandData.setForm((DataForm) dataFormProvider.parseExtension(parser));
+                }
+                else if (parser.getName().equals("note")) {
+                    AdHocCommandNote.Type type = AdHocCommandNote.Type.valueOf(
+                            parser.getAttributeValue("", "type"));
+                    String value = parser.nextText();
+                    adHocCommandData.addNote(new AdHocCommandNote(type, value));
+                }
+                else if (parser.getName().equals("error")) {
+                    XMPPError error = PacketParserUtils.parseError(parser);
+                    adHocCommandData.setError(error);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("command")) {
+                    done = true;
+                }
+            }
+        }
+        return adHocCommandData;
+    }
+
+    public static class BadActionError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.badAction);
+        }
+    }
+
+    public static class MalformedActionError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.malformedAction);
+        }
+    }
+
+    public static class BadLocaleError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.badLocale);
+        }
+    }
+
+    public static class BadPayloadError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.badPayload);
+        }
+    }
+
+    public static class BadSessionIDError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.badSessionid);
+        }
+    }
+
+    public static class SessionExpiredError implements PacketExtensionProvider {
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            return new AdHocCommandData.SpecificError(AdHocCommand.SpecificErrorCondition.sessionExpired);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/CapsExtensionProvider.java b/src/org/jivesoftware/smackx/provider/CapsExtensionProvider.java
new file mode 100644
index 0000000..5a7cd2f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/CapsExtensionProvider.java
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2009 Jonas Ådahl.
+ * Copyright 2011-2013 Florian Schmaus
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import java.io.IOException;
+
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.entitycaps.packet.CapsExtension;
+
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+public class CapsExtensionProvider implements PacketExtensionProvider {
+    private static final int MAX_DEPTH = 10;
+
+    public PacketExtension parseExtension(XmlPullParser parser) throws XmlPullParserException, IOException,
+            XMPPException {
+        String hash = null;
+        String version = null;
+        String node = null;
+        int depth = 0;
+        while (true) {
+            if (parser.getEventType() == XmlPullParser.START_TAG && parser.getName().equalsIgnoreCase("c")) {
+                hash = parser.getAttributeValue(null, "hash");
+                version = parser.getAttributeValue(null, "ver");
+                node = parser.getAttributeValue(null, "node");
+            }
+
+            if (parser.getEventType() == XmlPullParser.END_TAG && parser.getName().equalsIgnoreCase("c")) {
+                break;
+            } else {
+                parser.next();
+            }
+
+            if (depth < MAX_DEPTH) {
+                depth++;
+            } else {
+                throw new XMPPException("Malformed caps element");
+            }
+        }
+
+        if (hash != null && version != null && node != null) {
+            return new CapsExtension(node, version, hash);
+        } else {
+            throw new XMPPException("Caps elment with missing attributes");
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/DataFormProvider.java b/src/org/jivesoftware/smackx/provider/DataFormProvider.java
new file mode 100644
index 0000000..c13f234
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/DataFormProvider.java
@@ -0,0 +1,160 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * The DataFormProvider parses DataForm packets.
+ * 
+ * @author Gaston Dombiak
+ */
+public class DataFormProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new DataFormProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument constructor
+     */
+    public DataFormProvider() {
+    }
+
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        StringBuilder buffer = null;
+        DataForm dataForm = new DataForm(parser.getAttributeValue("", "type"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("instructions")) { 
+                    dataForm.addInstruction(parser.nextText());
+                }
+                else if (parser.getName().equals("title")) {                    
+                    dataForm.setTitle(parser.nextText());
+                }
+                else if (parser.getName().equals("field")) {                    
+                    dataForm.addField(parseField(parser));
+                }
+                else if (parser.getName().equals("item")) {                    
+                    dataForm.addItem(parseItem(parser));
+                }
+                else if (parser.getName().equals("reported")) {                    
+                    dataForm.setReportedData(parseReported(parser));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(dataForm.getElementName())) {
+                    done = true;
+                }
+            }
+        }
+        return dataForm;
+    }
+
+    private FormField parseField(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        FormField formField = new FormField(parser.getAttributeValue("", "var"));
+        formField.setLabel(parser.getAttributeValue("", "label"));
+        formField.setType(parser.getAttributeValue("", "type"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("desc")) { 
+                    formField.setDescription(parser.nextText());
+                }
+                else if (parser.getName().equals("value")) {                    
+                    formField.addValue(parser.nextText());
+                }
+                else if (parser.getName().equals("required")) {                    
+                    formField.setRequired(true);
+                }
+                else if (parser.getName().equals("option")) {                    
+                    formField.addOption(parseOption(parser));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("field")) {
+                    done = true;
+                }
+            }
+        }
+        return formField;
+    }
+
+    private DataForm.Item parseItem(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        List<FormField> fields = new ArrayList<FormField>();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("field")) { 
+                    fields.add(parseField(parser));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    done = true;
+                }
+            }
+        }
+        return new DataForm.Item(fields);
+    }
+
+    private DataForm.ReportedData parseReported(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        List<FormField> fields = new ArrayList<FormField>();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("field")) { 
+                    fields.add(parseField(parser));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("reported")) {
+                    done = true;
+                }
+            }
+        }
+        return new DataForm.ReportedData(fields);
+    }
+
+    private FormField.Option parseOption(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        FormField.Option option = null;
+        String label = parser.getAttributeValue("", "label");
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("value")) {
+                    option = new FormField.Option(label, parser.nextText());                     
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("option")) {
+                    done = true;
+                }
+            }
+        }
+        return option;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/DelayInfoProvider.java b/src/org/jivesoftware/smackx/provider/DelayInfoProvider.java
new file mode 100644
index 0000000..6fa52b7
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/DelayInfoProvider.java
@@ -0,0 +1,42 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.DelayInfo;
+import org.jivesoftware.smackx.packet.DelayInformation;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * This provider simply creates a {@link DelayInfo} decorator for the {@link DelayInformation} that
+ * is returned by the superclass.  This allows the new code using
+ * <a href="http://xmpp.org/extensions/xep-0203.html">Delay Information XEP-0203</a> to be
+ * backward compatible with <a href="http://xmpp.org/extensions/xep-0091.html">XEP-0091</a>.  
+ * 
+ * <p>This provider must be registered in the <b>smack.properties</b> file for the element 
+ * <b>delay</b> with namespace <b>urn:xmpp:delay</b></p>
+ *  
+ * @author Robin Collier
+ */
+public class DelayInfoProvider extends DelayInformationProvider
+{
+
+	@Override
+	public PacketExtension parseExtension(XmlPullParser parser) throws Exception
+	{
+		return new DelayInfo((DelayInformation)super.parseExtension(parser));
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/DelayInformationProvider.java b/src/org/jivesoftware/smackx/provider/DelayInformationProvider.java
new file mode 100644
index 0000000..e5fe010
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/DelayInformationProvider.java
@@ -0,0 +1,74 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import java.text.ParseException;
+import java.util.Date;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.DelayInformation;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The DelayInformationProvider parses DelayInformation packets.
+ * 
+ * @author Gaston Dombiak
+ * @author Henning Staib
+ */
+public class DelayInformationProvider implements PacketExtensionProvider {
+    
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        String stampString = (parser.getAttributeValue("", "stamp"));
+        Date stamp = null;
+        
+        try {
+            stamp = StringUtils.parseDate(stampString);
+        }
+        catch (ParseException parseExc) {
+            /*
+             * if date could not be parsed but XML is valid, don't shutdown
+             * connection by throwing an exception instead set timestamp to epoch 
+             * so that it is obviously wrong. 
+             */
+            if (stamp == null) {
+                stamp = new Date(0);
+            }
+        }
+        
+        
+        DelayInformation delayInformation = new DelayInformation(stamp);
+        delayInformation.setFrom(parser.getAttributeValue("", "from"));
+        String reason = parser.nextText();
+
+        /*
+         * parser.nextText() returns empty string if there is no reason.
+         * DelayInformation API specifies that null should be returned in that
+         * case.
+         */
+        reason = "".equals(reason) ? null : reason;
+        delayInformation.setReason(reason);
+        
+        return delayInformation;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/DiscoverInfoProvider.java b/src/org/jivesoftware/smackx/provider/DiscoverInfoProvider.java
new file mode 100644
index 0000000..6ad6fef
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/DiscoverInfoProvider.java
@@ -0,0 +1,86 @@
+/**
+ * $RCSfile$
+ * $Revision: 7071 $
+ * $Date: 2007-02-12 08:59:05 +0800 (Mon, 12 Feb 2007) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+* The DiscoverInfoProvider parses Service Discovery information packets.
+*
+* @author Gaston Dombiak
+*/
+public class DiscoverInfoProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        DiscoverInfo discoverInfo = new DiscoverInfo();
+        boolean done = false;
+        DiscoverInfo.Feature feature = null;
+        DiscoverInfo.Identity identity = null;
+        String category = "";
+        String name = "";
+        String type = "";
+        String variable = "";
+        String lang = "";
+        discoverInfo.setNode(parser.getAttributeValue("", "node"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("identity")) {
+                    // Initialize the variables from the parsed XML
+                    category = parser.getAttributeValue("", "category");
+                    name = parser.getAttributeValue("", "name");
+                    type = parser.getAttributeValue("", "type");
+                    lang = parser.getAttributeValue(parser.getNamespace("xml"), "lang");
+                }
+                else if (parser.getName().equals("feature")) {
+                    // Initialize the variables from the parsed XML
+                    variable = parser.getAttributeValue("", "var");
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    discoverInfo.addExtension(PacketParserUtils.parsePacketExtension(parser
+                            .getName(), parser.getNamespace(), parser));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("identity")) {
+                    // Create a new identity and add it to the discovered info.
+                    identity = new DiscoverInfo.Identity(category, name, type);
+                    if (lang != null)
+                        identity.setLanguage(lang);
+                    discoverInfo.addIdentity(identity);
+                }
+                if (parser.getName().equals("feature")) {
+                    // Create a new feature and add it to the discovered info.
+                    discoverInfo.addFeature(variable);
+                }
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+
+        return discoverInfo;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/provider/DiscoverItemsProvider.java b/src/org/jivesoftware/smackx/provider/DiscoverItemsProvider.java
new file mode 100644
index 0000000..fcbe25f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/DiscoverItemsProvider.java
@@ -0,0 +1,69 @@
+/**
+ * $RCSfile$
+ * $Revision: 7071 $
+ * $Date: 2007-02-12 08:59:05 +0800 (Mon, 12 Feb 2007) $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.packet.*;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+* The DiscoverInfoProvider parses Service Discovery items packets.
+*
+* @author Gaston Dombiak
+*/
+public class DiscoverItemsProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        DiscoverItems discoverItems = new DiscoverItems();
+        boolean done = false;
+        DiscoverItems.Item item;
+        String jid = "";
+        String name = "";
+        String action = "";
+        String node = "";
+        discoverItems.setNode(parser.getAttributeValue("", "node"));
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG && "item".equals(parser.getName())) {
+                // Initialize the variables from the parsed XML
+                jid = parser.getAttributeValue("", "jid");
+                name = parser.getAttributeValue("", "name");
+                node = parser.getAttributeValue("", "node");
+                action = parser.getAttributeValue("", "action");
+            }
+            else if (eventType == XmlPullParser.END_TAG && "item".equals(parser.getName())) {
+                // Create a new Item and add it to DiscoverItems.
+                item = new DiscoverItems.Item(jid);
+                item.setName(name);
+                item.setNode(node);
+                item.setAction(action);
+                discoverItems.addItem(item);
+            }
+            else if (eventType == XmlPullParser.END_TAG && "query".equals(parser.getName())) {
+                done = true;
+            }
+        }
+
+        return discoverItems;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/provider/EmbeddedExtensionProvider.java b/src/org/jivesoftware/smackx/provider/EmbeddedExtensionProvider.java
new file mode 100644
index 0000000..3d5ceb4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/EmbeddedExtensionProvider.java
@@ -0,0 +1,111 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.pubsub.provider.ItemProvider;
+import org.jivesoftware.smackx.pubsub.provider.ItemsProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * 
+ * This class simplifies parsing of embedded elements by using the 
+ * <a href="http://en.wikipedia.org/wiki/Template_method_pattern">Template Method Pattern</a>.  
+ * After extracting the current element attributes and content of any child elements, the template method 
+ * ({@link #createReturnExtension(String, String, Map, List)} is called.  Subclasses
+ * then override this method to create the specific return type.
+ * 
+ * <p>To use this class, you simply register your subclasses as extension providers in the 
+ * <b>smack.properties</b> file.  Then they will be automatically picked up and used to parse
+ * any child elements.  
+ * 
+ * <pre>
+ * For example, given the following message
+ * 
+ * &lt;message from='pubsub.shakespeare.lit' to='francisco@denmark.lit' id='foo&gt;
+ *    &lt;event xmlns='http://jabber.org/protocol/pubsub#event&gt;
+ *       &lt;items node='princely_musings'&gt;
+ *          &lt;item id='asdjkwei3i34234n356'&gt;
+ *             &lt;entry xmlns='http://www.w3.org/2005/Atom'&gt;
+ *                &lt;title&gt;Soliloquy&lt;/title&gt;
+ *                &lt;link rel='alternative' type='text/html'/&gt;
+ *                &lt;id>tag:denmark.lit,2003:entry-32397&lt;/id&gt;
+ *             &lt;/entry&gt;
+ *          &lt;/item&gt;
+ *       &lt;/items&gt;
+ *    &lt;/event&gt;
+ * &lt;/message&gt;
+ * 
+ * I would have a classes
+ * {@link ItemsProvider} extends {@link EmbeddedExtensionProvider}
+ * {@link ItemProvider} extends {@link EmbeddedExtensionProvider}
+ * and
+ * AtomProvider extends {@link PacketExtensionProvider}
+ * 
+ * These classes are then registered in the meta-inf/smack.providers file
+ * as follows.
+ * 
+ *   &lt;extensionProvider&gt;
+ *      &lt;elementName&gt;items&lt;/elementName&gt;
+ *      &lt;namespace&gt;http://jabber.org/protocol/pubsub#event&lt;/namespace&gt;
+ *      &lt;className&gt;org.jivesoftware.smackx.provider.ItemsEventProvider&lt;/className&gt;
+ *   &lt;/extensionProvider&gt;
+ *   &lt;extensionProvider&gt;
+ *       &lt;elementName&gt;item&lt;/elementName&gt;
+ *       &lt;namespace&gt;http://jabber.org/protocol/pubsub#event&lt;/namespace&gt;
+ *       &lt;className&gt;org.jivesoftware.smackx.provider.ItemProvider&lt;/className&gt;
+ *   &lt;/extensionProvider&gt;
+ * 
+ * </pre>
+ * 
+ * @author Robin Collier
+ * 
+ * @deprecated This has been moved to {@link org.jivesoftware.smack.provider.EmbeddedExtensionProvider}
+ */
+abstract public class EmbeddedExtensionProvider implements PacketExtensionProvider
+{
+
+	final public PacketExtension parseExtension(XmlPullParser parser) throws Exception
+	{
+        String namespace = parser.getNamespace();
+        String name = parser.getName();
+        Map<String, String> attMap = new HashMap<String, String>();
+        
+        for(int i=0; i<parser.getAttributeCount(); i++)
+        {
+        	attMap.put(parser.getAttributeName(i), parser.getAttributeValue(i));
+        }
+        List<PacketExtension> extensions = new ArrayList<PacketExtension>();
+        
+        do
+        {
+            int tag = parser.next();
+
+            if (tag == XmlPullParser.START_TAG) 
+            	extensions.add(PacketParserUtils.parsePacketExtension(parser.getName(), parser.getNamespace(), parser));
+        } while (!name.equals(parser.getName()));
+
+		return createReturnExtension(name, namespace, attMap, extensions);
+	}
+
+	abstract protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content);
+}
diff --git a/src/org/jivesoftware/smackx/provider/HeaderProvider.java b/src/org/jivesoftware/smackx/provider/HeaderProvider.java
new file mode 100644
index 0000000..7344880
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/HeaderProvider.java
@@ -0,0 +1,44 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.packet.Header;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses the header element as defined in <a href="http://xmpp.org/extensions/xep-0131">Stanza Headers and Internet Metadata (SHIM)</a>.
+ * 
+ * @author Robin Collier
+ */
+public class HeaderProvider implements PacketExtensionProvider
+{
+	public PacketExtension parseExtension(XmlPullParser parser) throws Exception
+	{
+		String name = parser.getAttributeValue(null, "name");
+		String value = null;
+		
+		parser.next();
+		
+		if (parser.getEventType() == XmlPullParser.TEXT)
+			value = parser.getText();
+		
+		while(parser.getEventType() != XmlPullParser.END_TAG)
+			parser.next();
+		
+		return new Header(name, value);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/HeadersProvider.java b/src/org/jivesoftware/smackx/provider/HeadersProvider.java
new file mode 100644
index 0000000..056dd58
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/HeadersProvider.java
@@ -0,0 +1,37 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.provider;
+
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.Header;
+import org.jivesoftware.smackx.packet.HeadersExtension;
+
+/**
+ * Parses the headers element as defined in <a href="http://xmpp.org/extensions/xep-0131">Stanza Headers and Internet Metadata (SHIM)</a>.
+ * 
+ * @author Robin Collier
+ */
+public class HeadersProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+		return new HeadersExtension((Collection<Header>)content);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/MUCAdminProvider.java b/src/org/jivesoftware/smackx/provider/MUCAdminProvider.java
new file mode 100644
index 0000000..1072232
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/MUCAdminProvider.java
@@ -0,0 +1,81 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smackx.packet.MUCAdmin;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The MUCAdminProvider parses MUCAdmin packets. (@see MUCAdmin)
+ * 
+ * @author Gaston Dombiak
+ */
+public class MUCAdminProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        MUCAdmin mucAdmin = new MUCAdmin();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                    mucAdmin.addItem(parseItem(parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+
+        return mucAdmin;
+    }
+
+    private MUCAdmin.Item parseItem(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCAdmin.Item item =
+            new MUCAdmin.Item(
+                parser.getAttributeValue("", "affiliation"),
+                parser.getAttributeValue("", "role"));
+        item.setNick(parser.getAttributeValue("", "nick"));
+        item.setJid(parser.getAttributeValue("", "jid"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("actor")) {
+                    item.setActor(parser.getAttributeValue("", "jid"));
+                }
+                if (parser.getName().equals("reason")) {
+                    item.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    done = true;
+                }
+            }
+        }
+        return item;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/MUCOwnerProvider.java b/src/org/jivesoftware/smackx/provider/MUCOwnerProvider.java
new file mode 100644
index 0000000..ff3094e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/MUCOwnerProvider.java
@@ -0,0 +1,108 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.*;
+import org.jivesoftware.smack.provider.*;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.packet.MUCOwner;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The MUCOwnerProvider parses MUCOwner packets. (@see MUCOwner)
+ * 
+ * @author Gaston Dombiak
+ */
+public class MUCOwnerProvider implements IQProvider {
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        MUCOwner mucOwner = new MUCOwner();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                    mucOwner.addItem(parseItem(parser));
+                }
+                else if (parser.getName().equals("destroy")) {
+                    mucOwner.setDestroy(parseDestroy(parser));
+                }
+                // Otherwise, it must be a packet extension.
+                else {
+                    mucOwner.addExtension(PacketParserUtils.parsePacketExtension(parser.getName(),
+                            parser.getNamespace(), parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+        }
+
+        return mucOwner;
+    }
+
+    private MUCOwner.Item parseItem(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCOwner.Item item = new MUCOwner.Item(parser.getAttributeValue("", "affiliation"));
+        item.setNick(parser.getAttributeValue("", "nick"));
+        item.setRole(parser.getAttributeValue("", "role"));
+        item.setJid(parser.getAttributeValue("", "jid"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("actor")) {
+                    item.setActor(parser.getAttributeValue("", "jid"));
+                }
+                if (parser.getName().equals("reason")) {
+                    item.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    done = true;
+                }
+            }
+        }
+        return item;
+    }
+
+    private MUCOwner.Destroy parseDestroy(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCOwner.Destroy destroy = new MUCOwner.Destroy();
+        destroy.setJid(parser.getAttributeValue("", "jid"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("reason")) {
+                    destroy.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("destroy")) {
+                    done = true;
+                }
+            }
+        }
+        return destroy;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/MUCUserProvider.java b/src/org/jivesoftware/smackx/provider/MUCUserProvider.java
new file mode 100644
index 0000000..5a98af6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/MUCUserProvider.java
@@ -0,0 +1,174 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.*;
+import org.jivesoftware.smack.provider.*;
+import org.jivesoftware.smackx.packet.*;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The MUCUserProvider parses packets with extended presence information about 
+ * roles and affiliations.
+ *
+ * @author Gaston Dombiak
+ */
+public class MUCUserProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new MUCUserProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument 
+     * constructor
+     */
+    public MUCUserProvider() {
+    }
+
+    /**
+     * Parses a MUCUser packet (extension sub-packet).
+     *
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        MUCUser mucUser = new MUCUser();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("invite")) {
+                    mucUser.setInvite(parseInvite(parser));
+                }
+                if (parser.getName().equals("item")) {
+                    mucUser.setItem(parseItem(parser));
+                }
+                if (parser.getName().equals("password")) {
+                    mucUser.setPassword(parser.nextText());
+                }
+                if (parser.getName().equals("status")) {
+                    mucUser.setStatus(new MUCUser.Status(parser.getAttributeValue("", "code")));
+                }
+                if (parser.getName().equals("decline")) {
+                    mucUser.setDecline(parseDecline(parser));
+                }
+                if (parser.getName().equals("destroy")) {
+                    mucUser.setDestroy(parseDestroy(parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("x")) {
+                    done = true;
+                }
+            }
+        }
+
+        return mucUser;
+    }
+
+    private MUCUser.Item parseItem(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCUser.Item item =
+            new MUCUser.Item(
+                parser.getAttributeValue("", "affiliation"),
+                parser.getAttributeValue("", "role"));
+        item.setNick(parser.getAttributeValue("", "nick"));
+        item.setJid(parser.getAttributeValue("", "jid"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("actor")) {
+                    item.setActor(parser.getAttributeValue("", "jid"));
+                }
+                if (parser.getName().equals("reason")) {
+                    item.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+                    done = true;
+                }
+            }
+        }
+        return item;
+    }
+
+    private MUCUser.Invite parseInvite(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCUser.Invite invite = new MUCUser.Invite();
+        invite.setFrom(parser.getAttributeValue("", "from"));
+        invite.setTo(parser.getAttributeValue("", "to"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("reason")) {
+                    invite.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("invite")) {
+                    done = true;
+                }
+            }
+        }
+        return invite;
+    }
+
+    private MUCUser.Decline parseDecline(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCUser.Decline decline = new MUCUser.Decline();
+        decline.setFrom(parser.getAttributeValue("", "from"));
+        decline.setTo(parser.getAttributeValue("", "to"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("reason")) {
+                    decline.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("decline")) {
+                    done = true;
+                }
+            }
+        }
+        return decline;
+    }
+
+    private MUCUser.Destroy parseDestroy(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MUCUser.Destroy destroy = new MUCUser.Destroy();
+        destroy.setJid(parser.getAttributeValue("", "jid"));
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("reason")) {
+                    destroy.setReason(parser.nextText());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("destroy")) {
+                    done = true;
+                }
+            }
+        }
+        return destroy;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/MessageEventProvider.java b/src/org/jivesoftware/smackx/provider/MessageEventProvider.java
new file mode 100644
index 0000000..b631546
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/MessageEventProvider.java
@@ -0,0 +1,77 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.packet.MessageEvent;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ *
+ * The MessageEventProvider parses Message Event packets.
+*
+ * @author Gaston Dombiak
+ */
+public class MessageEventProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new MessageEventProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument constructor
+     */
+    public MessageEventProvider() {
+    }
+
+    /**
+     * Parses a MessageEvent packet (extension sub-packet).
+     *
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser)
+        throws Exception {
+        MessageEvent messageEvent = new MessageEvent();
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("id"))
+                    messageEvent.setPacketID(parser.nextText());
+                if (parser.getName().equals(MessageEvent.COMPOSING))
+                    messageEvent.setComposing(true);
+                if (parser.getName().equals(MessageEvent.DELIVERED))
+                    messageEvent.setDelivered(true);
+                if (parser.getName().equals(MessageEvent.DISPLAYED))
+                    messageEvent.setDisplayed(true);
+                if (parser.getName().equals(MessageEvent.OFFLINE))
+                    messageEvent.setOffline(true);
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("x")) {
+                    done = true;
+                }
+            }
+        }
+
+        return messageEvent;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/MultipleAddressesProvider.java b/src/org/jivesoftware/smackx/provider/MultipleAddressesProvider.java
new file mode 100644
index 0000000..4c3e356
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/MultipleAddressesProvider.java
@@ -0,0 +1,67 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.packet.MultipleAddresses;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The MultipleAddressesProvider parses {@link MultipleAddresses} packets.
+ *
+ * @author Gaston Dombiak
+ */
+public class MultipleAddressesProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new MultipleAddressesProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument
+     * constructor.
+     */
+    public MultipleAddressesProvider() {
+    }
+
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        boolean done = false;
+        MultipleAddresses multipleAddresses = new MultipleAddresses();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("address")) {
+                    String type = parser.getAttributeValue("", "type");
+                    String jid = parser.getAttributeValue("", "jid");
+                    String node = parser.getAttributeValue("", "node");
+                    String desc = parser.getAttributeValue("", "desc");
+                    boolean delivered = "true".equals(parser.getAttributeValue("", "delivered"));
+                    String uri = parser.getAttributeValue("", "uri");
+                    // Add the parsed address
+                    multipleAddresses.addAddress(type, jid, node, desc, delivered, uri);
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals(multipleAddresses.getElementName())) {
+                    done = true;
+                }
+            }
+        }
+        return multipleAddresses;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/PEPProvider.java b/src/org/jivesoftware/smackx/provider/PEPProvider.java
new file mode 100644
index 0000000..f33dcde
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/PEPProvider.java
@@ -0,0 +1,93 @@
+/**
+ * $RCSfile: PEPProvider.java,v $
+ * $Revision: 1.2 $
+ * $Date: 2007/11/06 02:05:09 $
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ *
+ * The PEPProvider parses incoming PEPEvent packets.
+ * (XEP-163 has a weird asymmetric deal: outbound PEP are <iq> + <pubsub> and inbound are <message> + <event>.
+ * The provider only deals with inbound, and so it only deals with <message>.
+ * 
+ * Anyhoo...
+ * 
+ * The way this works is that PEPxxx classes are generic <pubsub> and <message> providers, and anyone who
+ * wants to publish/receive PEPs, such as <tune>, <geoloc>, etc., simply need to extend PEPItem and register (here)
+ * a PacketExtensionProvider that knows how to parse that PEPItem extension.
+ *
+ * @author Jeff Williams
+ */
+public class PEPProvider implements PacketExtensionProvider {
+
+    Map<String, PacketExtensionProvider> nodeParsers = new HashMap<String, PacketExtensionProvider>();
+    PacketExtension pepItem;
+    
+    /**
+     * Creates a new PEPProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument constructor
+     */
+    public PEPProvider() {
+    }
+
+    public void registerPEPParserExtension(String node, PacketExtensionProvider pepItemParser) {
+        nodeParsers.put(node, pepItemParser);
+    }
+
+    /**
+     * Parses a PEPEvent packet and extracts a PEPItem from it.
+     * (There is only one per <event>.)
+     *
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("event")) {
+                } else if (parser.getName().equals("items")) {
+                    // Figure out the node for this event.
+                    String node = parser.getAttributeValue("", "node");
+                    // Get the parser for this kind of node, and if found then parse the node.
+                    PacketExtensionProvider nodeParser = nodeParsers.get(node);
+                    if (nodeParser != null) {
+                        pepItem = nodeParser.parseExtension(parser);
+                    }
+                 }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("event")) {
+                    done = true;
+                }
+            }
+        }
+
+        return pepItem;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/PrivateDataProvider.java b/src/org/jivesoftware/smackx/provider/PrivateDataProvider.java
new file mode 100644
index 0000000..b781a5a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/PrivateDataProvider.java
@@ -0,0 +1,46 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.xmlpull.v1.XmlPullParser;
+import org.jivesoftware.smackx.packet.PrivateData;
+
+/**
+ * An interface for parsing custom private data. Each PrivateDataProvider must
+ * be registered with the PrivateDataManager class for it to be used. Every implementation
+ * of this interface <b>must</b> have a public, no-argument constructor.
+ *
+ * @author Matt Tucker
+ */
+public interface PrivateDataProvider {
+
+    /**
+     * Parse the private data sub-document and create a PrivateData instance. At the
+     * beginning of the method call, the xml parser will be positioned at the opening
+     * tag of the private data child element. At the end of the method call, the parser
+     * <b>must</b> be positioned on the closing tag of the child element.
+     *
+     * @param parser an XML parser.
+     * @return a new PrivateData instance.
+     * @throws Exception if an error occurs parsing the XML.
+     */
+    public PrivateData parsePrivateData(XmlPullParser parser) throws Exception;
+}
diff --git a/src/org/jivesoftware/smackx/provider/RosterExchangeProvider.java b/src/org/jivesoftware/smackx/provider/RosterExchangeProvider.java
new file mode 100644
index 0000000..76e09be
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/RosterExchangeProvider.java
@@ -0,0 +1,90 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import java.util.ArrayList;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.*;
+import org.jivesoftware.smackx.packet.*;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ *
+ * The RosterExchangeProvider parses RosterExchange packets.
+ *
+ * @author Gaston Dombiak
+ */
+public class RosterExchangeProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new RosterExchangeProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument constructor
+     */
+    public RosterExchangeProvider() {
+    }
+
+    /**
+     * Parses a RosterExchange packet (extension sub-packet).
+     *
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+
+        RosterExchange rosterExchange = new RosterExchange();
+        boolean done = false;
+        RemoteRosterEntry remoteRosterEntry = null;
+		String jid = "";
+		String name = "";
+		ArrayList<String> groupsName = new ArrayList<String>();
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("item")) {
+                	// Reset this variable since they are optional for each item
+					groupsName = new ArrayList<String>();
+					// Initialize the variables from the parsed XML
+                    jid = parser.getAttributeValue("", "jid");
+                    name = parser.getAttributeValue("", "name");
+                }
+                if (parser.getName().equals("group")) {
+					groupsName.add(parser.nextText());
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("item")) {
+					// Create packet.
+					remoteRosterEntry = new RemoteRosterEntry(jid, name, (String[]) groupsName.toArray(new String[groupsName.size()]));
+                    rosterExchange.addRosterEntry(remoteRosterEntry);
+                }
+                if (parser.getName().equals("x")) {
+                    done = true;
+                }
+            }
+        }
+
+        return rosterExchange;
+
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/StreamInitiationProvider.java b/src/org/jivesoftware/smackx/provider/StreamInitiationProvider.java
new file mode 100644
index 0000000..8101e4c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/StreamInitiationProvider.java
@@ -0,0 +1,124 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2006 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.provider;
+
+import java.text.ParseException;
+import java.util.Date;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.packet.StreamInitiation;
+import org.jivesoftware.smackx.packet.StreamInitiation.File;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The StreamInitiationProvider parses StreamInitiation packets.
+ * 
+ * @author Alexander Wenckus
+ * 
+ */
+public class StreamInitiationProvider implements IQProvider {
+
+	public IQ parseIQ(final XmlPullParser parser) throws Exception {
+		boolean done = false;
+
+		// si
+		String id = parser.getAttributeValue("", "id");
+		String mimeType = parser.getAttributeValue("", "mime-type");
+
+		StreamInitiation initiation = new StreamInitiation();
+
+		// file
+		String name = null;
+		String size = null;
+		String hash = null;
+		String date = null;
+		String desc = null;
+		boolean isRanged = false;
+
+		// feature
+		DataForm form = null;
+		DataFormProvider dataFormProvider = new DataFormProvider();
+
+		int eventType;
+		String elementName;
+		String namespace;
+		while (!done) {
+			eventType = parser.next();
+			elementName = parser.getName();
+			namespace = parser.getNamespace();
+			if (eventType == XmlPullParser.START_TAG) {
+				if (elementName.equals("file")) {
+					name = parser.getAttributeValue("", "name");
+					size = parser.getAttributeValue("", "size");
+					hash = parser.getAttributeValue("", "hash");
+					date = parser.getAttributeValue("", "date");
+				} else if (elementName.equals("desc")) {
+					desc = parser.nextText();
+				} else if (elementName.equals("range")) {
+					isRanged = true;
+				} else if (elementName.equals("x")
+						&& namespace.equals("jabber:x:data")) {
+					form = (DataForm) dataFormProvider.parseExtension(parser);
+				}
+			} else if (eventType == XmlPullParser.END_TAG) {
+				if (elementName.equals("si")) {
+					done = true;
+				} else if (elementName.equals("file")) {
+                    long fileSize = 0;
+                    if(size != null && size.trim().length() !=0){
+                        try {
+                            fileSize = Long.parseLong(size);
+                        }
+                        catch (NumberFormatException e) {
+                            e.printStackTrace();
+                        }
+                    }
+                    
+                    Date fileDate = new Date();
+                    if (date != null) {
+                        try {
+                            fileDate = StringUtils.parseXEP0082Date(date);
+                        } catch (ParseException e) {
+                            // couldn't parse date, use current date-time
+                        }
+                    }
+                    
+                    File file = new File(name, fileSize);
+					file.setHash(hash);
+					file.setDate(fileDate);
+					file.setDesc(desc);
+					file.setRanged(isRanged);
+					initiation.setFile(file);
+				}
+			}
+		}
+
+		initiation.setSesssionID(id);
+		initiation.setMimeType(mimeType);
+
+		initiation.setFeatureNegotiationForm(form);
+
+		return initiation;
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/VCardProvider.java b/src/org/jivesoftware/smackx/provider/VCardProvider.java
new file mode 100644
index 0000000..8fa0421
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/VCardProvider.java
@@ -0,0 +1,293 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.VCard;
+import org.w3c.dom.*;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+import javax.xml.parsers.DocumentBuilder;
+import javax.xml.parsers.DocumentBuilderFactory;
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * vCard provider.
+ *
+ * @author Gaston Dombiak
+ * @author Derek DeMoro
+ */
+public class VCardProvider implements IQProvider {
+
+    private static final String PREFERRED_ENCODING = "UTF-8";
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        final StringBuilder sb = new StringBuilder();
+        try {
+            int event = parser.getEventType();
+            // get the content
+            while (true) {
+                switch (event) {
+                    case XmlPullParser.TEXT:
+                        // We must re-escape the xml so that the DOM won't throw an exception
+                        sb.append(StringUtils.escapeForXML(parser.getText()));
+                        break;
+                    case XmlPullParser.START_TAG:
+                        sb.append('<').append(parser.getName()).append('>');
+                        break;
+                    case XmlPullParser.END_TAG:
+                        sb.append("</").append(parser.getName()).append('>');
+                        break;
+                    default:
+                }
+
+                if (event == XmlPullParser.END_TAG && "vCard".equals(parser.getName())) break;
+
+                event = parser.next();
+            }
+        }
+        catch (XmlPullParserException e) {
+            e.printStackTrace();
+        }
+        catch (IOException e) {
+            e.printStackTrace();
+        }
+
+        String xmlText = sb.toString();
+        return createVCardFromXML(xmlText);
+    }
+
+    /**
+     * Builds a users vCard from xml file.
+     *
+     * @param xml the xml representing a users vCard.
+     * @return the VCard.
+     * @throws Exception if an exception occurs.
+     */
+    public static VCard createVCardFromXML(String xml) throws Exception {
+        VCard vCard = new VCard();
+
+        DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
+        DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
+        Document document = documentBuilder.parse(
+                new ByteArrayInputStream(xml.getBytes(PREFERRED_ENCODING)));
+
+        new VCardReader(vCard, document).initializeFields();
+        return vCard;
+    }
+
+    private static class VCardReader {
+
+        private final VCard vCard;
+        private final Document document;
+
+        VCardReader(VCard vCard, Document document) {
+            this.vCard = vCard;
+            this.document = document;
+        }
+
+        public void initializeFields() {
+            vCard.setFirstName(getTagContents("GIVEN"));
+            vCard.setLastName(getTagContents("FAMILY"));
+            vCard.setMiddleName(getTagContents("MIDDLE"));
+            setupPhoto();
+
+            setupEmails();
+
+            vCard.setOrganization(getTagContents("ORGNAME"));
+            vCard.setOrganizationUnit(getTagContents("ORGUNIT"));
+
+            setupSimpleFields();
+
+            setupPhones();
+            setupAddresses();
+        }
+
+        private void setupPhoto() {
+            String binval = null;
+            String mimetype = null;
+
+            NodeList photo = document.getElementsByTagName("PHOTO");
+            if (photo.getLength() != 1)
+                return;
+
+            Node photoNode = photo.item(0);
+            NodeList childNodes = photoNode.getChildNodes();
+
+            int childNodeCount = childNodes.getLength();
+            List<Node> nodes = new ArrayList<Node>(childNodeCount);
+            for (int i = 0; i < childNodeCount; i++)
+                nodes.add(childNodes.item(i));
+
+            String name = null;
+            String value = null;
+            for (Node n : nodes) {
+                name = n.getNodeName();
+                value = n.getTextContent();
+                if (name.equals("BINVAL")) {
+                    binval = value;
+                }
+                else if (name.equals("TYPE")) {
+                    mimetype = value;
+                }
+            }
+
+            if (binval == null || mimetype == null)
+                return;
+
+            vCard.setAvatar(binval, mimetype);
+        }
+
+        private void setupEmails() {
+            NodeList nodes = document.getElementsByTagName("USERID");
+            if (nodes == null) return;
+            for (int i = 0; i < nodes.getLength(); i++) {
+                Element element = (Element) nodes.item(i);
+                if ("WORK".equals(element.getParentNode().getFirstChild().getNodeName())) {
+                    vCard.setEmailWork(getTextContent(element));
+                }
+                else {
+                    vCard.setEmailHome(getTextContent(element));
+                }
+            }
+        }
+
+        private void setupPhones() {
+            NodeList allPhones = document.getElementsByTagName("TEL");
+            if (allPhones == null) return;
+            for (int i = 0; i < allPhones.getLength(); i++) {
+                NodeList nodes = allPhones.item(i).getChildNodes();
+                String type = null;
+                String code = null;
+                String value = null;
+                for (int j = 0; j < nodes.getLength(); j++) {
+                    Node node = nodes.item(j);
+                    if (node.getNodeType() != Node.ELEMENT_NODE) continue;
+                    String nodeName = node.getNodeName();
+                    if ("NUMBER".equals(nodeName)) {
+                        value = getTextContent(node);
+                    }
+                    else if (isWorkHome(nodeName)) {
+                        type = nodeName;
+                    }
+                    else {
+                        code = nodeName;
+                    }
+                }
+                if (code == null || value == null) continue;
+                if ("HOME".equals(type)) {
+                    vCard.setPhoneHome(code, value);
+                }
+                else { // By default, setup work phone
+                    vCard.setPhoneWork(code, value);
+                }
+            }
+        }
+
+        private boolean isWorkHome(String nodeName) {
+            return "HOME".equals(nodeName) || "WORK".equals(nodeName);
+        }
+
+        private void setupAddresses() {
+            NodeList allAddresses = document.getElementsByTagName("ADR");
+            if (allAddresses == null) return;
+            for (int i = 0; i < allAddresses.getLength(); i++) {
+                Element addressNode = (Element) allAddresses.item(i);
+
+                String type = null;
+                List<String> code = new ArrayList<String>();
+                List<String> value = new ArrayList<String>();
+                NodeList childNodes = addressNode.getChildNodes();
+                for (int j = 0; j < childNodes.getLength(); j++) {
+                    Node node = childNodes.item(j);
+                    if (node.getNodeType() != Node.ELEMENT_NODE) continue;
+                    String nodeName = node.getNodeName();
+                    if (isWorkHome(nodeName)) {
+                        type = nodeName;
+                    }
+                    else {
+                        code.add(nodeName);
+                        value.add(getTextContent(node));
+                    }
+                }
+                for (int j = 0; j < value.size(); j++) {
+                    if ("HOME".equals(type)) {
+                        vCard.setAddressFieldHome((String) code.get(j), (String) value.get(j));
+                    }
+                    else { // By default, setup work address
+                        vCard.setAddressFieldWork((String) code.get(j), (String) value.get(j));
+                    }
+                }
+            }
+        }
+
+        private String getTagContents(String tag) {
+            NodeList nodes = document.getElementsByTagName(tag);
+            if (nodes != null && nodes.getLength() == 1) {
+                return getTextContent(nodes.item(0));
+            }
+            return null;
+        }
+
+        private void setupSimpleFields() {
+            NodeList childNodes = document.getDocumentElement().getChildNodes();
+            for (int i = 0; i < childNodes.getLength(); i++) {
+                Node node = childNodes.item(i);
+                if (node instanceof Element) {
+                    Element element = (Element) node;
+
+                    String field = element.getNodeName();
+                    if (element.getChildNodes().getLength() == 0) {
+                        vCard.setField(field, "");
+                    }
+                    else if (element.getChildNodes().getLength() == 1 &&
+                            element.getChildNodes().item(0) instanceof Text) {
+                        vCard.setField(field, getTextContent(element));
+                    }
+                }
+            }
+        }
+
+        private String getTextContent(Node node) {
+            StringBuilder result = new StringBuilder();
+            appendText(result, node);
+            return result.toString();
+        }
+
+        private void appendText(StringBuilder result, Node node) {
+            NodeList childNodes = node.getChildNodes();
+            for (int i = 0; i < childNodes.getLength(); i++) {
+                Node nd = childNodes.item(i);
+                String nodeValue = nd.getNodeValue();
+                if (nodeValue != null) {
+                    result.append(nodeValue);
+                }
+                appendText(result, nd);
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/provider/XHTMLExtensionProvider.java b/src/org/jivesoftware/smackx/provider/XHTMLExtensionProvider.java
new file mode 100644
index 0000000..50f437f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/XHTMLExtensionProvider.java
@@ -0,0 +1,94 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.packet.XHTMLExtension;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * The XHTMLExtensionProvider parses XHTML packets.
+ *
+ * @author Gaston Dombiak
+ */
+public class XHTMLExtensionProvider implements PacketExtensionProvider {
+
+    /**
+     * Creates a new XHTMLExtensionProvider.
+     * ProviderManager requires that every PacketExtensionProvider has a public, no-argument constructor
+     */
+    public XHTMLExtensionProvider() {
+    }
+
+    /**
+     * Parses a XHTMLExtension packet (extension sub-packet).
+     *
+     * @param parser the XML parser, positioned at the starting element of the extension.
+     * @return a PacketExtension.
+     * @throws Exception if a parsing error occurs.
+     */
+    public PacketExtension parseExtension(XmlPullParser parser)
+        throws Exception {
+        XHTMLExtension xhtmlExtension = new XHTMLExtension();
+        boolean done = false;
+        StringBuilder buffer = new StringBuilder();
+        int startDepth = parser.getDepth();
+        int depth = parser.getDepth();
+        String lastTag = "";
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("body")) {
+                    buffer = new StringBuilder();
+                    depth = parser.getDepth();
+                }
+                lastTag = parser.getText();
+                buffer.append(parser.getText());
+            } else if (eventType == XmlPullParser.TEXT) {
+                if (buffer != null) {
+                    // We need to return valid XML so any inner text needs to be re-escaped
+                    buffer.append(StringUtils.escapeForXML(parser.getText()));
+                }
+            } else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("body") && parser.getDepth() <= depth) {
+                    buffer.append(parser.getText());
+                    xhtmlExtension.addBody(buffer.toString());
+                }
+                else if (parser.getName().equals(xhtmlExtension.getElementName())
+                        && parser.getDepth() <= startDepth) {
+                    done = true;
+                }
+                else {
+                    // This is a check for tags that are both a start and end tag like <br/>
+                    // So that they aren't doubled
+                    if(lastTag == null || !lastTag.equals(parser.getText())) {
+                        buffer.append(parser.getText());
+                    }
+                }
+            }
+        }
+
+        return xhtmlExtension;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/provider/package.html b/src/org/jivesoftware/smackx/provider/package.html
new file mode 100644
index 0000000..962ba63
--- /dev/null
+++ b/src/org/jivesoftware/smackx/provider/package.html
@@ -0,0 +1 @@
+<body>Provides pluggable parsing logic for Smack extensions.</body>
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/pubsub/AccessModel.java b/src/org/jivesoftware/smackx/pubsub/AccessModel.java
new file mode 100644
index 0000000..c1fa546
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/AccessModel.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * This enumeration represents the access models for the pubsub node
+ * as defined in the pubsub specification section <a href="http://xmpp.org/extensions/xep-0060.html#registrar-formtypes-config">16.4.3</a>
+ * 
+ * @author Robin Collier
+ */
+public enum AccessModel
+{
+	/** Anyone may subscribe and retrieve items	 */
+	open,
+
+	/** Subscription request must be approved and only subscribers may retrieve items */
+	authorize,
+	
+	/** Anyone with a presence subscription of both or from may subscribe and retrieve items */
+	presence,
+	
+	/** Anyone in the specified roster group(s) may subscribe and retrieve items */
+	roster,
+	
+	/** Only those on a whitelist may subscribe and retrieve items */
+	whitelist;
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/Affiliation.java b/src/org/jivesoftware/smackx/pubsub/Affiliation.java
new file mode 100644
index 0000000..d55534d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/Affiliation.java
@@ -0,0 +1,111 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents a affiliation between a user and a node, where the {@link #type} defines 
+ * the type of affiliation.
+ * 
+ * Affiliations are retrieved from the {@link PubSubManager#getAffiliations()} method, which 
+ * gets affiliations for the calling user, based on the identity that is associated with 
+ * the {@link Connection}.
+ * 
+ * @author Robin Collier
+ */
+public class Affiliation implements PacketExtension
+{
+	protected String jid;
+	protected String node;
+	protected Type type;
+	
+	public enum Type
+	{
+		member, none, outcast, owner, publisher
+	}
+
+	/**
+	 * Constructs an affiliation.
+	 * 
+	 * @param jid The JID with affiliation.
+	 * @param affiliation The type of affiliation.
+	 */
+	public Affiliation(String jid, Type affiliation)
+	{
+		this(jid, null, affiliation);
+	}
+	
+	/**
+	 * Constructs an affiliation.
+	 * 
+	 * @param jid The JID with affiliation.
+	 * @param node The node with affiliation.
+	 * @param affiliation The type of affiliation.
+	 */
+	public Affiliation(String jid, String node, Type affiliation)
+	{
+		this.jid = jid;
+		this.node = node;
+		type = affiliation;
+	}
+	
+	public String getJid()
+	{
+		return jid;
+	}
+	
+	public String getNode()
+	{
+		return node;
+	}
+	
+	public Type getType()
+	{
+		return type;
+	}
+	
+	public String getElementName()
+	{
+		return "affiliation";
+	}
+
+	public String getNamespace()
+	{
+		return null;
+	}
+
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		if (node != null)
+			appendAttribute(builder, "node", node);
+		appendAttribute(builder, "jid", jid);
+		appendAttribute(builder, "affiliation", type.toString());
+		
+		builder.append("/>");
+		return builder.toString();
+	}
+
+	private void appendAttribute(StringBuilder builder, String att, String value)
+	{
+		builder.append(" ");
+		builder.append(att);
+		builder.append("='");
+		builder.append(value);
+		builder.append("'");
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/AffiliationsExtension.java b/src/org/jivesoftware/smackx/pubsub/AffiliationsExtension.java
new file mode 100644
index 0000000..563147e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/AffiliationsExtension.java
@@ -0,0 +1,91 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Represents the <b>affiliations</b> element of the reply to a request for affiliations.
+ * It is defined in the specification in section <a href="http://xmpp.org/extensions/xep-0060.html#entity-affiliations">5.7 Retrieve Affiliations</a>.
+ * 
+ * @author Robin Collier
+ */
+public class AffiliationsExtension extends NodeExtension
+{
+	protected List<Affiliation> items = Collections.EMPTY_LIST;
+	
+	public AffiliationsExtension()
+	{
+		super(PubSubElementType.AFFILIATIONS);
+	}
+	
+	public AffiliationsExtension(List<Affiliation> affiliationList)
+	{
+		super(PubSubElementType.AFFILIATIONS);
+
+		if (affiliationList != null)
+			items = affiliationList;
+	}
+
+	/**
+	 * Affiliations for the specified node.
+	 * 
+	 * @param nodeId
+	 * @param subList
+	 */
+	public AffiliationsExtension(String nodeId, List<Affiliation> affiliationList)
+	{
+		super(PubSubElementType.AFFILIATIONS, nodeId);
+
+		if (affiliationList != null)
+			items = affiliationList;
+	}
+
+	public List<Affiliation> getAffiliations()
+	{
+		return items;
+	}
+
+	@Override
+	public String toXML()
+	{
+		if ((items == null) || (items.size() == 0))
+		{
+			return super.toXML();
+		}
+		else
+		{
+			StringBuilder builder = new StringBuilder("<");
+			builder.append(getElementName());
+			if (getNode() != null)
+			{
+				builder.append(" node='");
+				builder.append(getNode());
+				builder.append("'");
+			}
+			builder.append(">");
+			
+			for (Affiliation item : items)
+			{
+				builder.append(item.toXML());
+			}
+			
+			builder.append("</");
+			builder.append(getElementName());
+			builder.append(">");
+			return builder.toString();
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ChildrenAssociationPolicy.java b/src/org/jivesoftware/smackx/pubsub/ChildrenAssociationPolicy.java
new file mode 100644
index 0000000..933a39e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ChildrenAssociationPolicy.java
@@ -0,0 +1,32 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * This enumeration represents the children association policy for associating leaf nodes
+ * with collection nodes as defined in the pubsub specification section <a href="http://xmpp.org/extensions/xep-0060.html#registrar-formtypes-config">16.4.3</a>
+ * 
+ * @author Robin Collier
+ */
+public enum ChildrenAssociationPolicy
+{
+	/** Anyone may associate leaf nodes with the collection	 */
+	all,
+	
+	/** Only collection node owners may associate leaf nodes with the collection. */
+	owners,
+	
+	/** Only those on a whitelist may associate leaf nodes with the collection.	 */
+	whitelist;
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/CollectionNode.java b/src/org/jivesoftware/smackx/pubsub/CollectionNode.java
new file mode 100644
index 0000000..dcd1cc4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/CollectionNode.java
@@ -0,0 +1,31 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Robin Collier.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.Connection;
+
+public class CollectionNode extends Node
+{
+	CollectionNode(Connection connection, String nodeId)
+	{
+		super(connection, nodeId);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ConfigurationEvent.java b/src/org/jivesoftware/smackx/pubsub/ConfigurationEvent.java
new file mode 100644
index 0000000..67b8304
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ConfigurationEvent.java
@@ -0,0 +1,56 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * Represents the <b>configuration</b> element of a pubsub message event which 
+ * associates a configuration form to the node which was configured.  The form 
+ * contains the current node configuration.
+ *  
+ * @author Robin Collier
+ */
+public class ConfigurationEvent extends NodeExtension implements EmbeddedPacketExtension
+{
+	private ConfigureForm form;
+	
+	public ConfigurationEvent(String nodeId)
+	{
+		super(PubSubElementType.CONFIGURATION, nodeId);
+	}
+	
+	public ConfigurationEvent(String nodeId, ConfigureForm configForm)
+	{
+		super(PubSubElementType.CONFIGURATION, nodeId);
+		form = configForm;
+	}
+	
+	public ConfigureForm getConfiguration()
+	{
+		return form;
+	}
+
+	public List<PacketExtension> getExtensions()
+	{
+		if (getConfiguration() == null)
+			return Collections.EMPTY_LIST;
+		else
+			return Arrays.asList(((PacketExtension)getConfiguration().getDataFormToSend()));
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ConfigureForm.java b/src/org/jivesoftware/smackx/pubsub/ConfigureForm.java
new file mode 100644
index 0000000..f6fe140
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ConfigureForm.java
@@ -0,0 +1,709 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.packet.DataForm;
+
+/**
+ * A decorator for a {@link Form} to easily enable reading and updating
+ * of node configuration.  All operations read or update the underlying {@link DataForm}.
+ * 
+ * <p>Unlike the {@link Form}.setAnswer(XXX)} methods, which throw an exception if the field does not
+ * exist, all <b>ConfigureForm.setXXX</b> methods will create the field in the wrapped form
+ * if it does not already exist. 
+ * 
+ * @author Robin Collier
+ */
+public class ConfigureForm extends Form
+{
+	/**
+	 * Create a decorator from an existing {@link DataForm} that has been
+	 * retrieved from parsing a node configuration request.
+	 * 
+	 * @param configDataForm
+	 */
+	public ConfigureForm(DataForm configDataForm)
+	{
+		super(configDataForm);
+	}
+	
+	/**
+	 * Create a decorator from an existing {@link Form} for node configuration.
+	 * Typically, this can be used to create a decorator for an answer form
+	 * by using the result of {@link #createAnswerForm()} as the input parameter.
+	 * 
+	 * @param nodeConfigForm
+	 */
+	public ConfigureForm(Form nodeConfigForm)
+	{
+		super(nodeConfigForm.getDataFormToSend());
+	}
+	
+	/**
+	 * Create a new form for configuring a node.  This would typically only be used 
+	 * when creating and configuring a node at the same time via {@link PubSubManager#createNode(String, Form)}, since 
+	 * configuration of an existing node is typically accomplished by calling {@link LeafNode#getNodeConfiguration()} and
+	 * using the resulting form to create a answer form.  See {@link #ConfigureForm(Form)}.
+	 * @param formType
+	 */
+	public ConfigureForm(FormType formType)
+	{
+		super(formType.toString());
+	}
+	
+	/**
+	 * Get the currently configured {@link AccessModel}, null if it is not set.
+	 * 
+	 * @return The current {@link AccessModel}
+	 */
+	public AccessModel getAccessModel()
+	{
+		String value = getFieldValue(ConfigureNodeFields.access_model);
+		
+		if (value == null)
+			return null;
+		else
+			return AccessModel.valueOf(value);
+	}
+	
+	/**
+	 * Sets the value of access model.
+	 * 
+	 * @param accessModel
+	 */
+	public void setAccessModel(AccessModel accessModel)
+	{
+		addField(ConfigureNodeFields.access_model, FormField.TYPE_LIST_SINGLE);
+		setAnswer(ConfigureNodeFields.access_model.getFieldName(), getListSingle(accessModel.toString()));
+	}
+
+	/**
+	 * Returns the URL of an XSL transformation which can be applied to payloads in order to 
+	 * generate an appropriate message body element.
+	 * 
+	 * @return URL to an XSL
+	 */
+	public String getBodyXSLT()
+	{
+		return getFieldValue(ConfigureNodeFields.body_xslt);
+	}
+
+	/**
+	 * Set the URL of an XSL transformation which can be applied to payloads in order to 
+	 * generate an appropriate message body element.
+	 * 
+	 * @param bodyXslt The URL of an XSL
+	 */
+	public void setBodyXSLT(String bodyXslt)
+	{
+		addField(ConfigureNodeFields.body_xslt, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.body_xslt.getFieldName(), bodyXslt);
+	}
+	
+	/**
+	 * The id's of the child nodes associated with a collection node (both leaf and collection).
+	 * 
+	 * @return Iterator over the list of child nodes.
+	 */
+	public Iterator<String> getChildren()
+	{
+		return getFieldValues(ConfigureNodeFields.children);
+	}
+	
+	/**
+	 * Set the list of child node ids that are associated with a collection node.
+	 * 
+	 * @param children
+	 */
+	public void setChildren(List<String> children)
+	{
+		addField(ConfigureNodeFields.children, FormField.TYPE_TEXT_MULTI);
+		setAnswer(ConfigureNodeFields.children.getFieldName(), children);
+	}
+	
+	/**
+	 * Returns the policy that determines who may associate children with the node.
+	 *  
+	 * @return The current policy
+	 */
+	public ChildrenAssociationPolicy getChildrenAssociationPolicy()
+	{
+		String value = getFieldValue(ConfigureNodeFields.children_association_policy);
+		
+		if (value == null)
+			return null;
+		else
+			return ChildrenAssociationPolicy.valueOf(value);
+	}
+	
+	/**
+	 * Sets the policy that determines who may associate children with the node.
+	 * 
+	 * @param policy The policy being set
+	 */
+	public void setChildrenAssociationPolicy(ChildrenAssociationPolicy policy)
+	{
+		addField(ConfigureNodeFields.children_association_policy, FormField.TYPE_LIST_SINGLE);
+        List<String> values = new ArrayList<String>(1);
+        values.add(policy.toString());
+        setAnswer(ConfigureNodeFields.children_association_policy.getFieldName(), values);
+	}
+	
+	/**
+	 * Iterator of JID's that are on the whitelist that determines who can associate child nodes 
+	 * with the collection node.  This is only relevant if {@link #getChildrenAssociationPolicy()} is set to
+	 * {@link ChildrenAssociationPolicy#whitelist}.
+	 * 
+	 * @return Iterator over whitelist
+	 */
+	public Iterator<String> getChildrenAssociationWhitelist()
+	{
+		return getFieldValues(ConfigureNodeFields.children_association_whitelist);
+	}
+	
+	/**
+	 * Set the JID's in the whitelist of users that can associate child nodes with the collection 
+	 * node.  This is only relevant if {@link #getChildrenAssociationPolicy()} is set to
+	 * {@link ChildrenAssociationPolicy#whitelist}.
+	 * 
+	 * @param whitelist The list of JID's
+	 */
+	public void setChildrenAssociationWhitelist(List<String> whitelist)
+	{
+		addField(ConfigureNodeFields.children_association_whitelist, FormField.TYPE_JID_MULTI);
+		setAnswer(ConfigureNodeFields.children_association_whitelist.getFieldName(), whitelist);
+	}
+
+	/**
+	 * Gets the maximum number of child nodes that can be associated with the collection node.
+	 * 
+	 * @return The maximum number of child nodes
+	 */
+	public int getChildrenMax()
+	{
+		return Integer.parseInt(getFieldValue(ConfigureNodeFields.children_max));
+	}
+
+	/**
+	 * Set the maximum number of child nodes that can be associated with a collection node.
+	 * 
+	 * @param max The maximum number of child nodes.
+	 */
+	public void setChildrenMax(int max)
+	{
+		addField(ConfigureNodeFields.children_max, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.children_max.getFieldName(), max);
+	}
+
+	/**
+	 * Gets the collection node which the node is affiliated with.
+	 * 
+	 * @return The collection node id
+	 */
+	public String getCollection()
+	{
+		return getFieldValue(ConfigureNodeFields.collection);
+	}
+
+	/**
+	 * Sets the collection node which the node is affiliated with.
+	 * 
+	 * @param collection The node id of the collection node
+	 */
+	public void setCollection(String collection)
+	{
+		addField(ConfigureNodeFields.collection, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.collection.getFieldName(), collection);
+	}
+
+	/**
+	 * Gets the URL of an XSL transformation which can be applied to the payload
+	 * format in order to generate a valid Data Forms result that the client could
+	 * display using a generic Data Forms rendering engine.
+	 * 
+	 * @return The URL of an XSL transformation
+	 */
+	public String getDataformXSLT()
+	{
+		return getFieldValue(ConfigureNodeFields.dataform_xslt);
+	}
+
+	/**
+	 * Sets the URL of an XSL transformation which can be applied to the payload
+	 * format in order to generate a valid Data Forms result that the client could
+	 * display using a generic Data Forms rendering engine.
+	 * 
+	 * @param url The URL of an XSL transformation
+	 */
+	public void setDataformXSLT(String url)
+	{
+		addField(ConfigureNodeFields.dataform_xslt, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.dataform_xslt.getFieldName(), url);
+	}
+
+	/**
+	 * Does the node deliver payloads with event notifications.
+	 * 
+	 * @return true if it does, false otherwise
+	 */
+	public boolean isDeliverPayloads()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.deliver_payloads));
+	}
+	
+	/**
+	 * Sets whether the node will deliver payloads with event notifications.
+	 * 
+	 * @param deliver true if the payload will be delivered, false otherwise
+	 */
+	public void setDeliverPayloads(boolean deliver)
+	{
+		addField(ConfigureNodeFields.deliver_payloads, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.deliver_payloads.getFieldName(), deliver);
+	}
+
+	/**
+	 * Determines who should get replies to items
+	 * 
+	 * @return Who should get the reply
+	 */
+	public ItemReply getItemReply()
+	{
+		String value = getFieldValue(ConfigureNodeFields.itemreply);
+		
+		if (value == null)
+			return null;
+		else
+			return ItemReply.valueOf(value);
+	}
+
+	/**
+	 * Sets who should get the replies to items
+	 * 
+	 * @param reply Defines who should get the reply
+	 */
+	public void setItemReply(ItemReply reply)
+	{
+		addField(ConfigureNodeFields.itemreply, FormField.TYPE_LIST_SINGLE);
+		setAnswer(ConfigureNodeFields.itemreply.getFieldName(), getListSingle(reply.toString()));
+	}
+
+	/**
+	 * Gets the maximum number of items to persisted to this node if {@link #isPersistItems()} is
+	 * true.
+	 * 
+	 * @return The maximum number of items to persist
+	 */
+	public int getMaxItems()
+	{
+		return Integer.parseInt(getFieldValue(ConfigureNodeFields.max_items));
+	}
+
+	/**
+	 * Set the maximum number of items to persisted to this node if {@link #isPersistItems()} is
+	 * true.
+	 * 
+	 * @param max The maximum number of items to persist
+	 */
+	public void setMaxItems(int max)
+	{
+		addField(ConfigureNodeFields.max_items, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.max_items.getFieldName(), max);
+	}
+	
+	/**
+	 * Gets the maximum payload size in bytes.
+	 * 
+	 * @return The maximum payload size
+	 */
+	public int getMaxPayloadSize()
+	{
+		return Integer.parseInt(getFieldValue(ConfigureNodeFields.max_payload_size));
+	}
+
+	/**
+	 * Sets the maximum payload size in bytes
+	 * 
+	 * @param max The maximum payload size
+	 */
+	public void setMaxPayloadSize(int max)
+	{
+		addField(ConfigureNodeFields.max_payload_size, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.max_payload_size.getFieldName(), max);
+	}
+	
+	/**
+	 * Gets the node type
+	 * 
+	 * @return The node type
+	 */
+	public NodeType getNodeType()
+	{
+		String value = getFieldValue(ConfigureNodeFields.node_type);
+		
+		if (value == null)
+			return null;
+		else
+			return NodeType.valueOf(value);
+	}
+	
+	/**
+	 * Sets the node type
+	 * 
+	 * @param type The node type
+	 */
+	public void setNodeType(NodeType type)
+	{
+		addField(ConfigureNodeFields.node_type, FormField.TYPE_LIST_SINGLE);
+		setAnswer(ConfigureNodeFields.node_type.getFieldName(), getListSingle(type.toString()));
+	}
+
+	/**
+	 * Determines if subscribers should be notified when the configuration changes.
+	 * 
+	 * @return true if they should be notified, false otherwise
+	 */
+	public boolean isNotifyConfig()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.notify_config));
+	}
+	
+	/**
+	 * Sets whether subscribers should be notified when the configuration changes.
+	 * 
+	 * @param notify true if subscribers should be notified, false otherwise
+	 */
+	public void setNotifyConfig(boolean notify)
+	{
+		addField(ConfigureNodeFields.notify_config, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.notify_config.getFieldName(), notify);
+	}
+
+	/**
+	 * Determines whether subscribers should be notified when the node is deleted.
+	 * 
+	 * @return true if subscribers should be notified, false otherwise
+	 */
+	public boolean isNotifyDelete()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.notify_delete));
+	}
+	
+	/**
+	 * Sets whether subscribers should be notified when the node is deleted.
+	 * 
+	 * @param notify true if subscribers should be notified, false otherwise
+	 */
+	public void setNotifyDelete(boolean notify) 
+	{
+		addField(ConfigureNodeFields.notify_delete, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.notify_delete.getFieldName(), notify);
+	}
+
+	/**
+	 * Determines whether subscribers should be notified when items are deleted 
+	 * from the node.
+	 * 
+	 * @return true if subscribers should be notified, false otherwise
+	 */
+	public boolean isNotifyRetract()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.notify_retract));
+	}
+	
+	/**
+	 * Sets whether subscribers should be notified when items are deleted 
+	 * from the node.
+	 * 
+	 * @param notify true if subscribers should be notified, false otherwise
+	 */
+	public void setNotifyRetract(boolean notify) 
+	{
+		addField(ConfigureNodeFields.notify_retract, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.notify_retract.getFieldName(), notify);
+	}
+	
+	/**
+	 * Determines whether items should be persisted in the node.
+	 * 
+	 * @return true if items are persisted
+	 */
+	public boolean isPersistItems()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.persist_items));
+	}
+	
+	/**
+	 * Sets whether items should be persisted in the node.
+	 * 
+	 * @param persist true if items should be persisted, false otherwise
+	 */
+	public void setPersistentItems(boolean persist) 
+	{
+		addField(ConfigureNodeFields.persist_items, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.persist_items.getFieldName(), persist);
+	}
+
+	/**
+	 * Determines whether to deliver notifications to available users only.
+	 * 
+	 * @return true if users must be available
+	 */
+	public boolean isPresenceBasedDelivery()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.presence_based_delivery));
+	}
+	
+	/**
+	 * Sets whether to deliver notifications to available users only.
+	 * 
+	 * @param presenceBased true if user must be available, false otherwise
+	 */
+	public void setPresenceBasedDelivery(boolean presenceBased) 
+	{
+		addField(ConfigureNodeFields.presence_based_delivery, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.presence_based_delivery.getFieldName(), presenceBased);
+	}
+
+	/**
+	 * Gets the publishing model for the node, which determines who may publish to it.
+	 * 
+	 * @return The publishing model
+	 */
+	public PublishModel getPublishModel()
+	{
+		String value = getFieldValue(ConfigureNodeFields.publish_model);
+		
+		if (value == null)
+			return null;
+		else
+			return PublishModel.valueOf(value);
+	}
+
+	/**
+	 * Sets the publishing model for the node, which determines who may publish to it.
+	 * 
+	 * @param publish The enum representing the possible options for the publishing model
+	 */
+	public void setPublishModel(PublishModel publish) 
+	{
+		addField(ConfigureNodeFields.publish_model, FormField.TYPE_LIST_SINGLE);
+		setAnswer(ConfigureNodeFields.publish_model.getFieldName(), getListSingle(publish.toString()));
+	}
+	
+	/**
+	 * Iterator over the multi user chat rooms that are specified as reply rooms.
+	 * 
+	 * @return The reply room JID's
+	 */
+	public Iterator<String> getReplyRoom()
+	{
+		return getFieldValues(ConfigureNodeFields.replyroom);
+	}
+	
+	/**
+	 * Sets the multi user chat rooms that are specified as reply rooms.
+	 * 
+	 * @param replyRooms The multi user chat room to use as reply rooms
+	 */
+	public void setReplyRoom(List<String> replyRooms) 
+	{
+		addField(ConfigureNodeFields.replyroom, FormField.TYPE_LIST_MULTI);
+		setAnswer(ConfigureNodeFields.replyroom.getFieldName(), replyRooms);
+	}
+	
+	/**
+	 * Gets the specific JID's for reply to.
+	 *  
+	 * @return The JID's
+	 */
+	public Iterator<String> getReplyTo()
+	{
+		return getFieldValues(ConfigureNodeFields.replyto);
+	}
+	
+	/**
+	 * Sets the specific JID's for reply to.
+	 * 
+	 * @param replyTos The JID's to reply to
+	 */
+	public void setReplyTo(List<String> replyTos)
+	{
+		addField(ConfigureNodeFields.replyto, FormField.TYPE_LIST_MULTI);
+		setAnswer(ConfigureNodeFields.replyto.getFieldName(), replyTos);
+	}
+	
+	/**
+	 * Gets the roster groups that are allowed to subscribe and retrieve items.
+	 *  
+	 * @return The roster groups
+	 */
+	public Iterator<String> getRosterGroupsAllowed()
+	{
+		return getFieldValues(ConfigureNodeFields.roster_groups_allowed);
+	}
+	
+	/**
+	 * Sets the roster groups that are allowed to subscribe and retrieve items.
+	 * 
+	 * @param groups The roster groups
+	 */
+	public void setRosterGroupsAllowed(List<String> groups)
+	{
+		addField(ConfigureNodeFields.roster_groups_allowed, FormField.TYPE_LIST_MULTI);
+		setAnswer(ConfigureNodeFields.roster_groups_allowed.getFieldName(), groups);
+	}
+	
+	/**
+	 * Determines if subscriptions are allowed.
+	 * 
+	 * @return true if subscriptions are allowed, false otherwise
+	 */
+	public boolean isSubscibe()
+	{
+		return parseBoolean(getFieldValue(ConfigureNodeFields.subscribe));
+	}
+
+	/**
+	 * Sets whether subscriptions are allowed.
+	 * 
+	 * @param subscribe true if they are, false otherwise
+	 */
+	public void setSubscribe(boolean subscribe)
+	{
+		addField(ConfigureNodeFields.subscribe, FormField.TYPE_BOOLEAN);
+		setAnswer(ConfigureNodeFields.subscribe.getFieldName(), subscribe);
+	}
+	
+	/**
+	 * Gets the human readable node title.
+	 * 
+	 * @return The node title
+	 */
+	public String getTitle()
+	{
+		return getFieldValue(ConfigureNodeFields.title);
+	}
+
+	/**
+	 * Sets a human readable title for the node.
+	 * 
+	 * @param title The node title
+	 */
+	public void setTitle(String title) 
+	{
+		addField(ConfigureNodeFields.title, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.title.getFieldName(), title);
+	}
+	
+	/**
+	 * The type of node data, usually specified by the namespace of the payload (if any).
+	 * 
+	 * @return The type of node data
+	 */
+	public String getDataType()
+	{
+		return getFieldValue(ConfigureNodeFields.type);
+	}
+
+	/**
+	 * Sets the type of node data, usually specified by the namespace of the payload (if any).
+	 * 
+	 * @param type The type of node data
+	 */
+	public void setDataType(String type) 
+	{
+		addField(ConfigureNodeFields.type, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(ConfigureNodeFields.type.getFieldName(), type);
+	}
+	
+	@Override
+	public String toString()
+	{
+		StringBuilder result = new StringBuilder(getClass().getName() + " Content [");
+		
+		Iterator<FormField> fields = getFields();
+		
+		while (fields.hasNext())
+		{
+			FormField formField = fields.next();
+			result.append('(');
+			result.append(formField.getVariable());
+			result.append(':');
+			
+			Iterator<String> values = formField.getValues();
+			StringBuilder valuesBuilder = new StringBuilder();
+				
+			while (values.hasNext())
+			{
+				if (valuesBuilder.length() > 0)
+					result.append(',');
+				String value = (String)values.next();
+				valuesBuilder.append(value);
+			}
+			
+			if (valuesBuilder.length() == 0)
+				valuesBuilder.append("NOT SET");
+			result.append(valuesBuilder);
+			result.append(')');
+		}
+		result.append(']');
+		return result.toString();
+	}
+
+	static private boolean parseBoolean(String fieldValue)
+	{
+		return ("1".equals(fieldValue) || "true".equals(fieldValue));
+	}
+
+	private String getFieldValue(ConfigureNodeFields field)
+	{
+		FormField formField = getField(field.getFieldName());
+		
+		return (formField.getValues().hasNext()) ? formField.getValues().next() : null;
+	}
+
+	private Iterator<String> getFieldValues(ConfigureNodeFields field)
+	{
+		FormField formField = getField(field.getFieldName());
+		
+		return formField.getValues();
+	}
+
+	private void addField(ConfigureNodeFields nodeField, String type)
+	{
+		String fieldName = nodeField.getFieldName();
+		
+		if (getField(fieldName) == null)
+		{
+			FormField field = new FormField(fieldName);
+			field.setType(type);
+			addField(field);
+		}
+	}
+
+	private List<String> getListSingle(String value)
+	{
+		List<String> list = new ArrayList<String>(1);
+		list.add(value);
+		return list;
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ConfigureNodeFields.java b/src/org/jivesoftware/smackx/pubsub/ConfigureNodeFields.java
new file mode 100644
index 0000000..3912483
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ConfigureNodeFields.java
@@ -0,0 +1,218 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.net.URL;
+
+import org.jivesoftware.smackx.Form;
+
+/**
+ * This enumeration represents all the fields of a node configuration form.  This enumeration
+ * is not required when using the {@link ConfigureForm} to configure nodes, but may be helpful
+ * for generic UI's using only a {@link Form} for configuration.
+ * 
+ * @author Robin Collier
+ */
+public enum ConfigureNodeFields
+{
+	/**
+	 * Determines who may subscribe and retrieve items
+	 * 
+	 * <p><b>Value: {@link AccessModel}</b></p>
+	 */
+	access_model,
+
+	/**
+	 * The URL of an XSL transformation which can be applied to 
+	 * payloads in order to generate an appropriate message
+	 * body element
+	 * 
+	 * <p><b>Value: {@link URL}</b></p>
+	 */
+	body_xslt,
+	
+	/**
+	 * The collection with which a node is affiliated
+	 * 
+	 * <p><b>Value: String</b></p>
+	 */
+	collection,
+
+	/**
+	 * The URL of an XSL transformation which can be applied to 
+	 * payload format in order to generate a valid Data Forms result 
+	 * that the client could display using a generic Data Forms 
+	 * rendering engine body element.
+	 * 
+	 * <p><b>Value: {@link URL}</b></p>
+	 */
+	dataform_xslt,
+
+	/**
+	 * Whether to deliver payloads with event notifications
+	 *
+	 * <p><b>Value: boolean</b></p>
+	 */
+	deliver_payloads,
+	
+	/**
+	 * Whether owners or publisher should receive replies to items
+	 *
+	 * <p><b>Value: {@link ItemReply}</b></p>
+	 */
+	itemreply,
+	
+	/**
+	 * Who may associate leaf nodes with a collection
+	 * 
+	 * <p><b>Value: {@link ChildrenAssociationPolicy}</b></p>
+	 */
+	children_association_policy,
+	
+	/**
+	 * The list of JIDs that may associate leaf nodes with a 
+	 * collection
+	 * 
+	 * <p><b>Value: List of JIDs as Strings</b></p>
+	 */
+	children_association_whitelist,
+	
+	/**
+	 * The child nodes (leaf or collection) associated with a collection
+	 * 
+	 * <p><b>Value: List of Strings</b></p>
+	 */
+	children,
+	
+	/**
+	 * The maximum number of child nodes that can be associated with a 
+	 * collection
+	 * 
+	 * <p><b>Value: int</b></p>
+	 */
+	children_max,
+	
+	/**
+	 * The maximum number of items to persist
+	 * 
+	 * <p><b>Value: int</b></p>
+	 */
+	max_items,
+	
+	/**
+	 * The maximum payload size in bytes
+	 * 
+	 * <p><b>Value: int</b></p>
+	 */
+	max_payload_size,
+	
+	/**
+	 * Whether the node is a leaf (default) or collection
+	 * 
+	 * <p><b>Value: {@link NodeType}</b></p>
+	 */
+	node_type,
+	
+	/**
+	 * Whether to notify subscribers when the node configuration changes
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	notify_config,
+	
+	/**
+	 * Whether to notify subscribers when the node is deleted
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	notify_delete,
+
+	/**
+	 * Whether to notify subscribers when items are removed from the node
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	notify_retract,
+	
+	/**
+	 * Whether to persist items to storage.  This is required to have multiple 
+	 * items in the node. 
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	persist_items,
+	
+	/**
+	 * Whether to deliver notifications to available users only
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	presence_based_delivery,
+
+	/**
+	 * Defines who can publish to the node
+	 * 
+	 * <p><b>Value: {@link PublishModel}</b></p>
+	 */
+	publish_model,
+	
+	/**
+	 * The specific multi-user chat rooms to specify for replyroom
+	 * 
+	 * <p><b>Value: List of JIDs as Strings</b></p>
+	 */
+	replyroom,
+	
+	/**
+	 * The specific JID(s) to specify for replyto
+	 * 
+	 * <p><b>Value: List of JIDs as Strings</b></p>
+	 */
+	replyto,
+	
+	/**
+	 * The roster group(s) allowed to subscribe and retrieve items
+	 * 
+	 * <p><b>Value: List of strings</b></p>
+	 */
+	roster_groups_allowed,
+	
+	/**
+	 * Whether to allow subscriptions
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	subscribe,
+	
+	/**
+	 * A friendly name for the node
+	 * 
+	 * <p><b>Value: String</b></p>
+	 */
+	title,
+	
+	/**
+	 * The type of node data, ussually specified by the namespace 
+	 * of the payload(if any);MAY be a list-single rather than a 
+	 * text single
+	 * 
+	 * <p><b>Value: String</b></p>
+	 */
+	type;
+	
+	public String getFieldName()
+	{
+		return "pubsub#" + toString();
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/EmbeddedPacketExtension.java b/src/org/jivesoftware/smackx/pubsub/EmbeddedPacketExtension.java
new file mode 100644
index 0000000..b17a66a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/EmbeddedPacketExtension.java
@@ -0,0 +1,45 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.List;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.util.PacketParserUtils;
+
+/**
+ * This interface defines {@link PacketExtension} implementations that contain other
+ * extensions.  This effectively extends the idea of an extension within one of the 
+ * top level {@link Packet} types to consider any embedded element to be an extension
+ * of its parent.  This more easily enables the usage of some of Smacks parsing
+ * utilities such as {@link PacketParserUtils#parsePacketExtension(String, String, org.xmlpull.v1.XmlPullParser)} to be used
+ * to parse any element of the XML being parsed.
+ * 
+ * <p>Top level extensions have only one element, but they can have multiple children, or
+ * their children can have multiple children.  This interface is a way of allowing extensions 
+ * to be embedded within one another as a partial or complete one to one mapping of extension 
+ * to element.
+ * 
+ * @author Robin Collier
+ */
+public interface EmbeddedPacketExtension extends PacketExtension
+{
+	/**
+	 * Get the list of embedded {@link PacketExtension} objects.
+	 *  
+	 * @return List of embedded {@link PacketExtension}
+	 */
+	List<PacketExtension> getExtensions();
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/EventElement.java b/src/org/jivesoftware/smackx/pubsub/EventElement.java
new file mode 100644
index 0000000..165970f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/EventElement.java
@@ -0,0 +1,74 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Arrays;
+import java.util.List;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+
+/**
+ * Represents the top level element of a pubsub event extension.  All types of pubsub events are
+ * represented by this class.  The specific type can be found by {@link #getEventType()}.  The 
+ * embedded event information, which is specific to the event type, can be retrieved by the {@link #getEvent()}
+ * method.
+ * 
+ * @author Robin Collier
+ */
+public class EventElement implements EmbeddedPacketExtension
+{
+	private EventElementType type;
+	private NodeExtension ext;
+	
+	public EventElement(EventElementType eventType, NodeExtension eventExt)
+	{
+		type = eventType;
+		ext = eventExt;
+	}
+	
+	public EventElementType getEventType()
+	{
+		return type;
+	}
+
+	public List<PacketExtension> getExtensions()
+	{
+		return Arrays.asList(new PacketExtension[]{getEvent()});
+	}
+
+	public NodeExtension getEvent()
+	{
+		return ext;
+	}
+
+	public String getElementName()
+	{
+		return "event";
+	}
+
+	public String getNamespace()
+	{
+		return PubSubNamespace.EVENT.getXmlns();
+	}
+
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<event xmlns='" + PubSubNamespace.EVENT.getXmlns() + "'>");
+
+		builder.append(ext.toXML());
+		builder.append("</event>");
+		return builder.toString();
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/EventElementType.java b/src/org/jivesoftware/smackx/pubsub/EventElementType.java
new file mode 100644
index 0000000..343edbe
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/EventElementType.java
@@ -0,0 +1,41 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * This enumeration defines the possible event types that are supported within pubsub
+ * event messages.
+ * 
+ * @author Robin Collier
+ */
+public enum EventElementType
+{
+	/** A node has been associated or dissassociated with a collection node */
+	collection, 
+
+	/** A node has had its configuration changed */
+	configuration, 
+	
+	/** A node has been deleted */
+	delete, 
+	
+	/** Items have been published to a node */
+	items, 
+	
+	/** All items have been purged from a node */
+	purge, 
+	
+	/** A node has been subscribed to */
+	subscription
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/FormNode.java b/src/org/jivesoftware/smackx/pubsub/FormNode.java
new file mode 100644
index 0000000..e08bed2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/FormNode.java
@@ -0,0 +1,99 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.Form;
+
+/**
+ * Generic packet extension which represents any pubsub form that is
+ * parsed from the incoming stream or being sent out to the server.
+ * 
+ * Form types are defined in {@link FormNodeType}.
+ * 
+ * @author Robin Collier
+ */
+public class FormNode extends NodeExtension
+{
+	private Form configForm;
+	
+	/**
+	 * Create a {@link FormNode} which contains the specified form.
+	 * 
+	 * @param formType The type of form being sent
+	 * @param submitForm The form
+	 */
+	public FormNode(FormNodeType formType, Form submitForm)
+	{
+		super(formType.getNodeElement());
+
+		if (submitForm == null)
+			throw new IllegalArgumentException("Submit form cannot be null");
+		configForm = submitForm;
+	}
+	
+	/**
+	 * Create a {@link FormNode} which contains the specified form, which is 
+	 * associated with the specified node.
+	 * 
+	 * @param formType The type of form being sent
+	 * @param nodeId The node the form is associated with
+	 * @param submitForm The form
+	 */
+	public FormNode(FormNodeType formType, String nodeId, Form submitForm)
+	{
+		super(formType.getNodeElement(), nodeId);
+
+		if (submitForm == null)
+			throw new IllegalArgumentException("Submit form cannot be null");
+		configForm = submitForm;
+	}
+	
+	/**
+	 * Get the Form that is to be sent, or was retrieved from the server.
+	 * 
+	 * @return The form
+	 */
+	public Form getForm()
+	{
+		return configForm;
+	}
+	
+	@Override
+	public String toXML()
+	{
+		if (configForm == null)
+		{
+			return super.toXML();
+		}
+		else
+		{
+			StringBuilder builder = new StringBuilder("<");
+			builder.append(getElementName());
+			
+			if (getNode() != null)
+			{
+				builder.append(" node='");
+				builder.append(getNode());
+				builder.append("'>");
+			}
+			else
+				builder.append('>');
+			builder.append(configForm.getDataFormToSend().toXML());
+			builder.append("</");
+			builder.append(getElementName() + '>');
+			return builder.toString();
+		}
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/FormNodeType.java b/src/org/jivesoftware/smackx/pubsub/FormNodeType.java
new file mode 100644
index 0000000..6a163ee
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/FormNodeType.java
@@ -0,0 +1,50 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+
+/**
+ * The types of forms supported by the pubsub specification.
+ * 
+ * @author Robin Collier
+ */
+public enum FormNodeType
+{
+	/** Form for configuring an existing node */
+	CONFIGURE_OWNER,
+	
+	/** Form for configuring a node during creation */
+	CONFIGURE,
+	
+	/** Form for configuring subscription options */
+	OPTIONS,
+
+	/** Form which represents the default node configuration options */
+	DEFAULT;
+	
+	public PubSubElementType getNodeElement()
+	{
+		return PubSubElementType.valueOf(toString());
+	}
+
+	public static FormNodeType valueOfFromElementName(String elem, String configNamespace)
+	{
+		if ("configure".equals(elem) && PubSubNamespace.OWNER.getXmlns().equals(configNamespace))
+		{
+			return CONFIGURE_OWNER;
+		}
+		return valueOf(elem.toUpperCase());
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/FormType.java b/src/org/jivesoftware/smackx/pubsub/FormType.java
new file mode 100644
index 0000000..e0fff51
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/FormType.java
@@ -0,0 +1,26 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.Form;
+
+/**
+ * Defines the allowable types for a {@link Form}
+ * 
+ * @author Robin Collier
+ */
+public enum FormType
+{
+    form, submit, cancel, result;
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/pubsub/GetItemsRequest.java b/src/org/jivesoftware/smackx/pubsub/GetItemsRequest.java
new file mode 100644
index 0000000..341b7b5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/GetItemsRequest.java
@@ -0,0 +1,85 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * Represents a request to subscribe to a node.
+ * 
+ * @author Robin Collier
+ */
+public class GetItemsRequest extends NodeExtension
+{
+	protected String subId;
+	protected int maxItems;
+	
+	public GetItemsRequest(String nodeId)
+	{
+		super(PubSubElementType.ITEMS, nodeId);
+	}
+	
+	public GetItemsRequest(String nodeId, String subscriptionId)
+	{
+		super(PubSubElementType.ITEMS, nodeId);
+		subId = subscriptionId;
+	}
+
+	public GetItemsRequest(String nodeId, int maxItemsToReturn)
+	{
+		super(PubSubElementType.ITEMS, nodeId);
+		maxItems = maxItemsToReturn;
+	}
+
+	public GetItemsRequest(String nodeId, String subscriptionId, int maxItemsToReturn)
+	{
+		this(nodeId, maxItemsToReturn);
+		subId = subscriptionId;
+	}
+
+	public String getSubscriptionId()
+	{
+		return subId;
+	}
+
+	public int getMaxItems()
+	{
+		return maxItems;
+	}
+
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		
+		builder.append(" node='");
+		builder.append(getNode());
+		builder.append("'");
+
+		if (getSubscriptionId() != null)
+		{
+			builder.append(" subid='");
+			builder.append(getSubscriptionId());
+			builder.append("'");
+		}
+
+		if (getMaxItems() > 0)
+		{
+			builder.append(" max_items='");
+			builder.append(getMaxItems());
+			builder.append("'");
+		}
+		builder.append("/>");
+		return builder.toString();
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/Item.java b/src/org/jivesoftware/smackx/pubsub/Item.java
new file mode 100644
index 0000000..2ce0baa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/Item.java
@@ -0,0 +1,132 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smackx.pubsub.provider.ItemProvider;
+
+/**
+ * This class represents an item that has been, or will be published to a
+ * pubsub node.  An <tt>Item</tt> has several properties that are dependent
+ * on the configuration of the node to which it has been or will be published.
+ * 
+ * <h1>An Item received from a node (via {@link LeafNode#getItems()} or {@link LeafNode#addItemEventListener(org.jivesoftware.smackx.pubsub.listener.ItemEventListener)}</b>
+ * <li>Will always have an id (either user or server generated) unless node configuration has both
+ * {@link ConfigureForm#isPersistItems()} and {@link ConfigureForm#isDeliverPayloads()}set to false.
+ * <li>Will have a payload if the node configuration has {@link ConfigureForm#isDeliverPayloads()} set 
+ * to true, otherwise it will be null.
+ * 
+ * <h1>An Item created to send to a node (via {@link LeafNode#send()} or {@link LeafNode#publish()}</b>
+ * <li>The id is optional, since the server will generate one if necessary, but should be used if it is 
+ * meaningful in the context of the node.  This value must be unique within the node that it is sent to, since
+ * resending an item with the same id will overwrite the one that already exists if the items are persisted.
+ * <li>Will require payload if the node configuration has {@link ConfigureForm#isDeliverPayloads()} set
+ * to true. 
+ * 
+ * <p>To customise the payload object being returned from the {@link #getPayload()} method, you can
+ * add a custom parser as explained in {@link ItemProvider}.
+ * 
+ * @author Robin Collier
+ */
+public class Item extends NodeExtension
+{
+	private String id;
+	
+	/**
+	 * Create an empty <tt>Item</tt> with no id.  This is a valid item for nodes which are configured
+	 * so that {@link ConfigureForm#isDeliverPayloads()} is false.  In most cases an id will be generated by the server.
+	 * For nodes configured with {@link ConfigureForm#isDeliverPayloads()} and {@link ConfigureForm#isPersistItems()} 
+	 * set to false, no <tt>Item</tt> is sent to the node, you have to use {@link LeafNode#send()} or {@link LeafNode#publish()}
+	 * methods in this case. 
+	 */
+	public Item()
+	{
+		super(PubSubElementType.ITEM);
+	}
+	
+	/**
+	 * Create an <tt>Item</tt> with an id but no payload.  This is a valid item for nodes which are configured
+	 * so that {@link ConfigureForm#isDeliverPayloads()} is false.
+	 * 
+	 * @param itemId The id if the item.  It must be unique within the node unless overwriting and existing item.
+	 * Passing null is the equivalent of calling {@link #Item()}.
+	 */
+	public Item(String itemId)
+	{
+		// The element type is actually irrelevant since we override getNamespace() to return null
+		super(PubSubElementType.ITEM);
+		id = itemId;
+	}
+
+	/**
+	 * Create an <tt>Item</tt> with an id and a node id.  
+	 * <p>
+	 * <b>Note:</b> This is not valid for publishing an item to a node, only receiving from 
+	 * one as part of {@link Message}.  If used to create an Item to publish 
+	 * (via {@link LeafNode#publish(Item)}, the server <i>may</i> return an
+	 * error for an invalid packet.
+	 * 
+	 * @param itemId The id of the item.
+	 * @param nodeId The id of the node which the item was published to.
+	 */
+    public Item(String itemId, String nodeId) 
+    {
+    	super(PubSubElementType.ITEM_EVENT, nodeId);
+        id = itemId;
+    }
+	
+	/**
+	 * Get the item id.  Unique to the node it is associated with.
+	 * 
+	 * @return The id
+	 */
+	public String getId()
+	{
+		return id;
+	}
+	
+	@Override
+	public String getNamespace()
+	{
+		return null;
+	}
+
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<item");
+		
+		if (id != null)
+		{
+			builder.append(" id='");
+			builder.append(id);
+			builder.append("'");
+		}
+		
+        if (getNode() != null) {
+            builder.append(" node='");
+            builder.append(getNode());
+            builder.append("'");
+        }
+		builder.append("/>");
+
+		return builder.toString();
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + " | Content [" + toXML() + "]";
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ItemDeleteEvent.java b/src/org/jivesoftware/smackx/pubsub/ItemDeleteEvent.java
new file mode 100644
index 0000000..82ab7df
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ItemDeleteEvent.java
@@ -0,0 +1,62 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Represents an event in which items have been deleted from the node.
+ * 
+ * @author Robin Collier
+ */
+public class ItemDeleteEvent extends SubscriptionEvent
+{
+	private List<String> itemIds = Collections.EMPTY_LIST;
+	
+	/**
+	 * Constructs an <tt>ItemDeleteEvent</tt> that indicates the the supplied
+	 * items (by id) have been deleted, and that the event matches the listed
+	 * subscriptions.  The subscriptions would have been created by calling 
+	 * {@link LeafNode#subscribe(String)}.
+	 * 
+	 * @param nodeId The id of the node the event came from
+	 * @param deletedItemIds The item ids of the items that were deleted.
+	 * @param subscriptionIds The subscriptions that match the event.
+	 */
+	public ItemDeleteEvent(String nodeId, List<String> deletedItemIds, List<String> subscriptionIds)
+	{
+		super(nodeId, subscriptionIds);
+		
+		if (deletedItemIds == null)
+			throw new IllegalArgumentException("deletedItemIds cannot be null");
+		itemIds = deletedItemIds;
+	}
+	
+	/**
+	 * Get the item id's of the items that have been deleted.
+	 * 
+	 * @return List of item id's
+	 */
+	public List<String> getItemIds()
+	{
+		return Collections.unmodifiableList(itemIds);
+	}
+	
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + "  [subscriptions: " + getSubscriptions() + "], [Deleted Items: " + itemIds + ']';
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ItemPublishEvent.java b/src/org/jivesoftware/smackx/pubsub/ItemPublishEvent.java
new file mode 100644
index 0000000..1ef1f67
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ItemPublishEvent.java
@@ -0,0 +1,123 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Collections;
+import java.util.Date;
+import java.util.List;
+
+/**
+ * Represents an event generated by an item(s) being published to a node.
+ * 
+ * @author Robin Collier
+ */
+public class ItemPublishEvent <T extends Item> extends SubscriptionEvent
+{
+	private List<T> items;
+	private Date originalDate;
+	
+	/**
+	 * Constructs an <tt>ItemPublishEvent</tt> with the provided list
+	 * of {@link Item} that were published.
+	 * 
+	 * @param nodeId The id of the node the event came from
+	 * @param eventItems The list of {@link Item} that were published 
+	 */
+	public ItemPublishEvent(String nodeId, List<T> eventItems)
+	{
+		super(nodeId);
+		items = eventItems;
+	}
+	
+	/**
+	 * Constructs an <tt>ItemPublishEvent</tt> with the provided list
+	 * of {@link Item} that were published.  The list of subscription ids
+	 * represents the subscriptions that matched the event, in the case 
+	 * of the user having multiple subscriptions.
+	 * 
+	 * @param nodeId The id of the node the event came from
+	 * @param eventItems The list of {@link Item} that were published 
+	 * @param subscriptionIds The list of subscriptionIds
+	 */
+	public ItemPublishEvent(String nodeId, List<T> eventItems, List<String> subscriptionIds)
+	{
+		super(nodeId, subscriptionIds);
+		items = eventItems;
+	}
+	
+	/**
+	 * Constructs an <tt>ItemPublishEvent</tt> with the provided list
+	 * of {@link Item} that were published in the past.  The published
+	 * date signifies that this is delayed event.  The list of subscription ids
+	 * represents the subscriptions that matched the event, in the case 
+	 * of the user having multiple subscriptions. 
+	 *
+	 * @param nodeId The id of the node the event came from
+	 * @param eventItems The list of {@link Item} that were published 
+	 * @param subscriptionIds The list of subscriptionIds
+	 * @param publishedDate The original publishing date of the events
+	 */
+	public ItemPublishEvent(String nodeId, List<T> eventItems, List<String> subscriptionIds, Date publishedDate)
+	{
+		super(nodeId, subscriptionIds);
+		items = eventItems;
+		
+		if (publishedDate != null)
+			originalDate = publishedDate;
+	}
+	
+	/**
+	 * Get the list of {@link Item} that were published.
+	 * 
+	 * @return The list of published {@link Item}
+	 */
+	public List<T> getItems()
+	{
+		return Collections.unmodifiableList(items);
+	}
+	
+	/**
+	 * Indicates whether this event was delayed.  That is, the items
+	 * were published to the node at some time in the past.  This will 
+	 * typically happen if there is an item already published to the node
+	 * before a user subscribes to it.  In this case, when the user 
+	 * subscribes, the server may send the last item published to the node
+	 * with a delay date showing its time of original publication.
+	 * 
+	 * @return true if the items are delayed, false otherwise.
+	 */
+	public boolean isDelayed()
+	{
+		return (originalDate != null);
+	}
+	
+	/**
+	 * Gets the original date the items were published.  This is only 
+	 * valid if {@link #isDelayed()} is true.
+	 * 
+	 * @return Date items were published if {@link #isDelayed()} is true, null otherwise.
+	 */
+	public Date getPublishedDate()
+	{
+		return originalDate;
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + "  [subscriptions: " + getSubscriptions() + "], [Delayed: " + 
+			(isDelayed() ? originalDate.toString() : "false") + ']';
+	}
+	
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ItemReply.java b/src/org/jivesoftware/smackx/pubsub/ItemReply.java
new file mode 100644
index 0000000..3e090d9
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ItemReply.java
@@ -0,0 +1,29 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * These are the options for the node configuration setting {@link ConfigureForm#setItemReply(ItemReply)},
+ * which defines who should receive replies to items.
+ * 
+ * @author Robin Collier
+ */
+public enum ItemReply
+{
+	/** The node owner */
+	owner,
+	
+	/** The item publisher */
+	publisher;
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/ItemsExtension.java b/src/org/jivesoftware/smackx/pubsub/ItemsExtension.java
new file mode 100644
index 0000000..c98d93a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/ItemsExtension.java
@@ -0,0 +1,196 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.List;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * This class is used to for multiple purposes.  
+ * <li>It can represent an event containing a list of items that have been published
+ * <li>It can represent an event containing a list of retracted (deleted) items.
+ * <li>It can represent a request to delete a list of items.
+ * <li>It can represent a request to get existing items.
+ * 
+ * <p><b>Please note, this class is used for internal purposes, and is not required for usage of 
+ * pubsub functionality.</b>
+ * 
+ * @author Robin Collier
+ */
+public class ItemsExtension extends NodeExtension implements EmbeddedPacketExtension
+{
+	protected ItemsElementType type;
+	protected Boolean notify;
+	protected List<? extends PacketExtension> items;
+
+	public enum ItemsElementType
+	{
+		/** An items element, which has an optional <b>max_items</b> attribute when requesting items */
+		items(PubSubElementType.ITEMS, "max_items"),
+		
+		/** A retract element, which has an optional <b>notify</b> attribute when publishing deletions */
+		retract(PubSubElementType.RETRACT, "notify");
+		
+		private PubSubElementType elem;
+		private String att;
+		
+		private ItemsElementType(PubSubElementType nodeElement, String attribute)
+		{
+			elem = nodeElement;
+			att = attribute;
+		}
+		
+		public PubSubElementType getNodeElement()
+		{
+			return elem;
+		}
+
+		public String getElementAttribute()
+		{
+			return att;
+		}
+	}
+
+	/**
+	 * Construct an instance with a list representing items that have been published or deleted.
+	 * 
+	 * <p>Valid scenarios are:
+	 * <li>Request items from node - itemsType = {@link ItemsElementType#items}, items = list of {@link Item} and an
+	 * optional value for the <b>max_items</b> attribute.
+	 * <li>Request to delete items - itemsType = {@link ItemsElementType#retract}, items = list of {@link Item} containing
+	 * only id's and an optional value for the <b>notify</b> attribute.
+	 * <li>Items published event - itemsType = {@link ItemsElementType#items}, items = list of {@link Item} and 
+	 * attributeValue = <code>null</code>
+	 * <li>Items deleted event -  itemsType = {@link ItemsElementType#items}, items = list of {@link RetractItem} and 
+	 * attributeValue = <code>null</code> 
+	 * 
+	 * @param itemsType Type of representation
+	 * @param nodeId The node to which the items are being sent or deleted
+	 * @param items The list of {@link Item} or {@link RetractItem}
+	 * @param attributeValue The value of the <b>max_items</b>  
+	 */
+	public ItemsExtension(ItemsElementType itemsType, String nodeId, List<? extends PacketExtension> items)
+	{
+		super(itemsType.getNodeElement(), nodeId);
+		type = itemsType;
+		this.items = items;
+	}
+	
+	/**
+	 * Construct an instance with a list representing items that have been published or deleted.
+	 * 
+	 * <p>Valid scenarios are:
+	 * <li>Request items from node - itemsType = {@link ItemsElementType#items}, items = list of {@link Item} and an
+	 * optional value for the <b>max_items</b> attribute.
+	 * <li>Request to delete items - itemsType = {@link ItemsElementType#retract}, items = list of {@link Item} containing
+	 * only id's and an optional value for the <b>notify</b> attribute.
+	 * <li>Items published event - itemsType = {@link ItemsElementType#items}, items = list of {@link Item} and 
+	 * attributeValue = <code>null</code>
+	 * <li>Items deleted event -  itemsType = {@link ItemsElementType#items}, items = list of {@link RetractItem} and 
+	 * attributeValue = <code>null</code> 
+	 * 
+	 * @param itemsType Type of representation
+	 * @param nodeId The node to which the items are being sent or deleted
+	 * @param items The list of {@link Item} or {@link RetractItem}
+	 * @param attributeValue The value of the <b>max_items</b>  
+	 */
+	public ItemsExtension(String nodeId, List<? extends PacketExtension> items, boolean notify)
+	{
+		super(ItemsElementType.retract.getNodeElement(), nodeId);
+		type = ItemsElementType.retract;
+		this.items = items; 
+		this.notify = notify;
+	}
+	
+	/**
+	 * Get the type of element
+	 * 
+	 * @return The element type
+	 */
+	public ItemsElementType getItemsElementType()
+	{
+		return type;
+	}
+	
+	public List<PacketExtension> getExtensions()
+	{
+		return (List<PacketExtension>)getItems();
+	}
+	
+	/**
+	 * Gets the items related to the type of request or event.
+	 * 
+	 * return List of {@link Item}, {@link RetractItem}, or null
+	 */
+	public List<? extends PacketExtension> getItems()
+	{
+		return items;
+	}
+
+	/**
+	 * Gets the value of the optional attribute related to the {@link ItemsElementType}.
+	 * 
+	 * @return The attribute value
+	 */
+	public boolean getNotify()
+	{
+		return notify;
+	}
+	
+	@Override
+	public String toXML()
+	{
+		if ((items == null) || (items.size() == 0))
+		{
+			return super.toXML();
+		}
+		else
+		{
+			StringBuilder builder = new StringBuilder("<");
+			builder.append(getElementName());
+			builder.append(" node='");
+			builder.append(getNode());
+			
+			if (notify != null)
+			{
+				builder.append("' ");
+				builder.append(type.getElementAttribute());
+				builder.append("='");
+				builder.append(notify.equals(Boolean.TRUE) ? 1 : 0);
+				builder.append("'>");
+			}
+			else
+			{
+				builder.append("'>");
+				for (PacketExtension item : items)
+				{
+					builder.append(item.toXML());
+				}
+			}
+			
+			builder.append("</");
+			builder.append(getElementName());
+			builder.append(">");
+			return builder.toString();
+		}
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + "Content [" + toXML() + "]";
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/LeafNode.java b/src/org/jivesoftware/smackx/pubsub/LeafNode.java
new file mode 100644
index 0000000..eee6293
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/LeafNode.java
@@ -0,0 +1,352 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ.Type;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.pubsub.packet.PubSub;
+import org.jivesoftware.smackx.pubsub.packet.SyncPacketSend;
+
+/**
+ * The main class for the majority of pubsub functionality.  In general
+ * almost all pubsub capabilities are related to the concept of a node.
+ * All items are published to a node, and typically subscribed to by other
+ * users.  These users then retrieve events based on this subscription.
+ * 
+ * @author Robin Collier
+ */
+public class LeafNode extends Node
+{
+	LeafNode(Connection connection, String nodeName)
+	{
+		super(connection, nodeName);
+	}
+	
+	/**
+	 * Get information on the items in the node in standard
+	 * {@link DiscoverItems} format.
+	 * 
+	 * @return The item details in {@link DiscoverItems} format
+	 * 
+	 * @throws XMPPException
+	 */
+	public DiscoverItems discoverItems()
+		throws XMPPException
+	{
+		DiscoverItems items = new DiscoverItems();
+		items.setTo(to);
+		items.setNode(getId());
+		return (DiscoverItems)SyncPacketSend.getReply(con, items);
+	}
+
+	/**
+	 * Get the current items stored in the node.
+	 * 
+	 * @return List of {@link Item} in the node
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> List<T> getItems()
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId()));
+		
+		PubSub result = (PubSub)SyncPacketSend.getReply(con, request);
+		ItemsExtension itemsElem = (ItemsExtension)result.getExtension(PubSubElementType.ITEMS);
+		return (List<T>)itemsElem.getItems();
+	}
+	
+	/**
+	 * Get the current items stored in the node based
+	 * on the subscription associated with the provided 
+	 * subscription id.
+	 * 
+	 * @param subscriptionId -  The subscription id for the 
+	 * associated subscription.
+	 * @return List of {@link Item} in the node
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> List<T> getItems(String subscriptionId)
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), subscriptionId));
+		
+		PubSub result = (PubSub)SyncPacketSend.getReply(con, request);
+		ItemsExtension itemsElem = (ItemsExtension)result.getExtension(PubSubElementType.ITEMS);
+		return (List<T>)itemsElem.getItems();
+	}
+
+	/**
+	 * Get the items specified from the node.  This would typically be
+	 * used when the server does not return the payload due to size 
+	 * constraints.  The user would be required to retrieve the payload 
+	 * after the items have been retrieved via {@link #getItems()} or an
+	 * event, that did not include the payload.
+	 * 
+	 * @param ids Item ids of the items to retrieve
+	 * 
+	 * @return The list of {@link Item} with payload
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> List<T> getItems(Collection<String> ids)
+		throws XMPPException
+	{
+		List<Item> itemList = new ArrayList<Item>(ids.size());
+		
+		for (String id : ids)
+		{
+			itemList.add(new Item(id));
+		}
+		PubSub request = createPubsubPacket(Type.GET, new ItemsExtension(ItemsExtension.ItemsElementType.items, getId(), itemList));
+		
+		PubSub result = (PubSub)SyncPacketSend.getReply(con, request);
+		ItemsExtension itemsElem = (ItemsExtension)result.getExtension(PubSubElementType.ITEMS);
+		return (List<T>)itemsElem.getItems();
+	}
+
+	/**
+	 * Get items persisted on the node, limited to the specified number.
+	 * 
+	 * @param maxItems Maximum number of items to return
+	 * 
+	 * @return List of {@link Item}
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> List<T> getItems(int maxItems)
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), maxItems));
+		
+		PubSub result = (PubSub)SyncPacketSend.getReply(con, request);
+		ItemsExtension itemsElem = (ItemsExtension)result.getExtension(PubSubElementType.ITEMS);
+		return (List<T>)itemsElem.getItems();
+	}
+	
+	/**
+	 * Get items persisted on the node, limited to the specified number
+	 * based on the subscription associated with the provided subscriptionId.
+	 * 
+	 * @param maxItems Maximum number of items to return
+	 * @param subscriptionId The subscription which the retrieval is based
+	 * on.
+	 * 
+	 * @return List of {@link Item}
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> List<T> getItems(int maxItems, String subscriptionId)
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.GET, new GetItemsRequest(getId(), subscriptionId, maxItems));
+		
+		PubSub result = (PubSub)SyncPacketSend.getReply(con, request);
+		ItemsExtension itemsElem = (ItemsExtension)result.getExtension(PubSubElementType.ITEMS);
+		return (List<T>)itemsElem.getItems();
+	}
+	
+	/**
+	 * Publishes an event to the node.  This is an empty event
+	 * with no item.
+	 * 
+	 * This is only acceptable for nodes with {@link ConfigureForm#isPersistItems()}=false
+	 * and {@link ConfigureForm#isDeliverPayloads()}=false.
+	 * 
+	 * This is an asynchronous call which returns as soon as the 
+	 * packet has been sent.
+	 * 
+	 * For synchronous calls use {@link #send() send()}.
+	 */
+	public void publish()
+	{
+		PubSub packet = createPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.PUBLISH, getId()));
+		
+		con.sendPacket(packet);
+	}
+	
+	/**
+	 * Publishes an event to the node.  This is a simple item
+	 * with no payload.
+	 * 
+	 * If the id is null, an empty item (one without an id) will be sent.
+	 * Please note that this is not the same as {@link #send()}, which
+	 * publishes an event with NO item.
+	 * 
+	 * This is an asynchronous call which returns as soon as the 
+	 * packet has been sent.
+	 * 
+	 * For synchronous calls use {@link #send(Item) send(Item))}.
+	 * 
+	 * @param item - The item being sent
+	 */
+	public <T extends Item> void publish(T item)
+	{
+		Collection<T> items = new ArrayList<T>(1);
+		items.add((T)(item == null ? new Item() : item));
+		publish(items);
+	}
+
+	/**
+	 * Publishes multiple events to the node.  Same rules apply as in {@link #publish(Item)}.
+	 * 
+	 * In addition, if {@link ConfigureForm#isPersistItems()}=false, only the last item in the input
+	 * list will get stored on the node, assuming it stores the last sent item.
+	 * 
+	 * This is an asynchronous call which returns as soon as the 
+	 * packet has been sent.
+	 * 
+	 * For synchronous calls use {@link #send(Collection) send(Collection))}.
+	 * 
+	 * @param items - The collection of items being sent
+	 */
+	public <T extends Item> void publish(Collection<T> items)
+	{
+		PubSub packet = createPubsubPacket(Type.SET, new PublishItem<T>(getId(), items));
+		
+		con.sendPacket(packet);
+	}
+
+	/**
+	 * Publishes an event to the node.  This is an empty event
+	 * with no item.
+	 * 
+	 * This is only acceptable for nodes with {@link ConfigureForm#isPersistItems()}=false
+	 * and {@link ConfigureForm#isDeliverPayloads()}=false.
+	 * 
+	 * This is a synchronous call which will throw an exception 
+	 * on failure.
+	 * 
+	 * For asynchronous calls, use {@link #publish() publish()}.
+	 * 
+	 * @throws XMPPException
+	 */
+	public void send()
+		throws XMPPException
+	{
+		PubSub packet = createPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.PUBLISH, getId()));
+		
+		SyncPacketSend.getReply(con, packet);
+	}
+	
+	/**
+	 * Publishes an event to the node.  This can be either a simple item
+	 * with no payload, or one with it.  This is determined by the Node
+	 * configuration.
+	 * 
+	 * If the node has <b>deliver_payload=false</b>, the Item must not
+	 * have a payload.
+	 * 
+	 * If the id is null, an empty item (one without an id) will be sent.
+	 * Please note that this is not the same as {@link #send()}, which
+	 * publishes an event with NO item.
+	 * 
+	 * This is a synchronous call which will throw an exception 
+	 * on failure.
+	 * 
+	 * For asynchronous calls, use {@link #publish(Item) publish(Item)}.
+	 * 
+	 * @param item - The item being sent
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> void send(T item)
+		throws XMPPException
+	{
+		Collection<T> items = new ArrayList<T>(1);
+		items.add((item == null ? (T)new Item() : item));
+		send(items);
+	}
+	
+	/**
+	 * Publishes multiple events to the node.  Same rules apply as in {@link #send(Item)}.
+	 * 
+	 * In addition, if {@link ConfigureForm#isPersistItems()}=false, only the last item in the input
+	 * list will get stored on the node, assuming it stores the last sent item.
+	 *  
+	 * This is a synchronous call which will throw an exception 
+	 * on failure.
+	 * 
+	 * For asynchronous calls, use {@link #publish(Collection) publish(Collection))}.
+	 * 
+	 * @param items - The collection of {@link Item} objects being sent
+	 * 
+	 * @throws XMPPException
+	 */
+	public <T extends Item> void send(Collection<T> items)
+		throws XMPPException
+	{
+		PubSub packet = createPubsubPacket(Type.SET, new PublishItem<T>(getId(), items));
+		
+		SyncPacketSend.getReply(con, packet);
+	}
+	
+	/**
+	 * Purges the node of all items.
+	 *   
+	 * <p>Note: Some implementations may keep the last item
+	 * sent.
+	 * 
+	 * @throws XMPPException
+	 */
+	public void deleteAllItems()
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.PURGE_OWNER, getId()), PubSubElementType.PURGE_OWNER.getNamespace());
+		
+		SyncPacketSend.getReply(con, request);
+	}
+	
+	/**
+	 * Delete the item with the specified id from the node.
+	 * 
+	 * @param itemId The id of the item
+	 * 
+	 * @throws XMPPException
+	 */
+	public void deleteItem(String itemId)
+		throws XMPPException
+	{
+		Collection<String> items = new ArrayList<String>(1);
+		items.add(itemId);
+		deleteItem(items);
+	}
+	
+	/**
+	 * Delete the items with the specified id's from the node.
+	 * 
+	 * @param itemIds The list of id's of items to delete
+	 * 
+	 * @throws XMPPException
+	 */
+	public void deleteItem(Collection<String> itemIds)
+		throws XMPPException
+	{
+		List<Item> items = new ArrayList<Item>(itemIds.size());
+		
+		for (String id : itemIds)
+		{
+			items.add(new Item(id));
+		}
+		PubSub request = createPubsubPacket(Type.SET, new ItemsExtension(ItemsExtension.ItemsElementType.retract, getId(), items));
+		SyncPacketSend.getReply(con, request);
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/Node.java b/src/org/jivesoftware/smackx/pubsub/Node.java
new file mode 100644
index 0000000..1b0ff5a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/Node.java
@@ -0,0 +1,541 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Robin Collier.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.OrFilter;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.packet.IQ.Type;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.packet.DelayInformation;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.Header;
+import org.jivesoftware.smackx.packet.HeadersExtension;
+import org.jivesoftware.smackx.pubsub.listener.ItemDeleteListener;
+import org.jivesoftware.smackx.pubsub.listener.ItemEventListener;
+import org.jivesoftware.smackx.pubsub.listener.NodeConfigListener;
+import org.jivesoftware.smackx.pubsub.packet.PubSub;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+import org.jivesoftware.smackx.pubsub.packet.SyncPacketSend;
+import org.jivesoftware.smackx.pubsub.util.NodeUtils;
+
+abstract public class Node
+{
+	protected Connection con;
+	protected String id;
+	protected String to;
+	
+	protected ConcurrentHashMap<ItemEventListener<Item>, PacketListener> itemEventToListenerMap = new ConcurrentHashMap<ItemEventListener<Item>, PacketListener>();
+	protected ConcurrentHashMap<ItemDeleteListener, PacketListener> itemDeleteToListenerMap = new ConcurrentHashMap<ItemDeleteListener, PacketListener>();
+	protected ConcurrentHashMap<NodeConfigListener, PacketListener> configEventToListenerMap = new ConcurrentHashMap<NodeConfigListener, PacketListener>();
+	
+	/**
+	 * Construct a node associated to the supplied connection with the specified 
+	 * node id.
+	 * 
+	 * @param connection The connection the node is associated with
+	 * @param nodeName The node id
+	 */
+	Node(Connection connection, String nodeName)
+	{
+		con = connection;
+		id = nodeName;
+	}
+
+	/**
+	 * Some XMPP servers may require a specific service to be addressed on the 
+	 * server.
+	 * 
+	 *   For example, OpenFire requires the server to be prefixed by <b>pubsub</b>
+	 */
+	void setTo(String toAddress)
+	{
+		to = toAddress;
+	}
+
+	/**
+	 * Get the NodeId
+	 * 
+	 * @return the node id
+	 */
+	public String getId() 
+	{
+		return id;
+	}
+	/**
+	 * Returns a configuration form, from which you can create an answer form to be submitted
+	 * via the {@link #sendConfigurationForm(Form)}.
+	 * 
+	 * @return the configuration form
+	 */
+	public ConfigureForm getNodeConfiguration()
+		throws XMPPException
+	{
+		Packet reply = sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.CONFIGURE_OWNER, getId()), PubSubNamespace.OWNER);
+		return NodeUtils.getFormFromPacket(reply, PubSubElementType.CONFIGURE_OWNER);
+	}
+	
+	/**
+	 * Update the configuration with the contents of the new {@link Form}
+	 * 
+	 * @param submitForm
+	 */
+	public void sendConfigurationForm(Form submitForm)
+		throws XMPPException
+	{
+		PubSub packet = createPubsubPacket(Type.SET, new FormNode(FormNodeType.CONFIGURE_OWNER, getId(), submitForm), PubSubNamespace.OWNER);
+		SyncPacketSend.getReply(con, packet);
+	}
+	
+	/**
+	 * Discover node information in standard {@link DiscoverInfo} format.
+	 * 
+	 * @return The discovery information about the node.
+	 * 
+	 * @throws XMPPException
+	 */
+	public DiscoverInfo discoverInfo()
+		throws XMPPException
+	{
+		DiscoverInfo info = new DiscoverInfo();
+		info.setTo(to);
+		info.setNode(getId());
+		return (DiscoverInfo)SyncPacketSend.getReply(con, info);
+	}
+	
+	/**
+	 * Get the subscriptions currently associated with this node.
+	 * 
+	 * @return List of {@link Subscription}
+	 * 
+	 * @throws XMPPException
+	 */
+	public List<Subscription> getSubscriptions()
+		throws XMPPException
+	{
+		PubSub reply = (PubSub)sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.SUBSCRIPTIONS, getId()));
+		SubscriptionsExtension subElem = (SubscriptionsExtension)reply.getExtension(PubSubElementType.SUBSCRIPTIONS);
+		return subElem.getSubscriptions();
+	}
+
+	/**
+	 * The user subscribes to the node using the supplied jid.  The
+	 * bare jid portion of this one must match the jid for the connection.
+	 * 
+	 * Please note that the {@link Subscription.State} should be checked 
+	 * on return since more actions may be required by the caller.
+	 * {@link Subscription.State#pending} - The owner must approve the subscription 
+	 * request before messages will be received.
+	 * {@link Subscription.State#unconfigured} - If the {@link Subscription#isConfigRequired()} is true, 
+	 * the caller must configure the subscription before messages will be received.  If it is false
+	 * the caller can configure it but is not required to do so.
+	 * @param jid The jid to subscribe as.
+	 * @return The subscription
+	 * @exception XMPPException
+	 */
+	public Subscription subscribe(String jid)
+		throws XMPPException
+	{
+		PubSub reply = (PubSub)sendPubsubPacket(Type.SET, new SubscribeExtension(jid, getId()));
+		return (Subscription)reply.getExtension(PubSubElementType.SUBSCRIPTION);
+	}
+	
+	/**
+	 * The user subscribes to the node using the supplied jid and subscription
+	 * options.  The bare jid portion of this one must match the jid for the 
+	 * connection.
+	 * 
+	 * Please note that the {@link Subscription.State} should be checked 
+	 * on return since more actions may be required by the caller.
+	 * {@link Subscription.State#pending} - The owner must approve the subscription 
+	 * request before messages will be received.
+	 * {@link Subscription.State#unconfigured} - If the {@link Subscription#isConfigRequired()} is true, 
+	 * the caller must configure the subscription before messages will be received.  If it is false
+	 * the caller can configure it but is not required to do so.
+	 * @param jid The jid to subscribe as.
+	 * @return The subscription
+	 * @exception XMPPException
+	 */
+	public Subscription subscribe(String jid, SubscribeForm subForm)
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(Type.SET, new SubscribeExtension(jid, getId()));
+		request.addExtension(new FormNode(FormNodeType.OPTIONS, subForm));
+		PubSub reply = (PubSub)PubSubManager.sendPubsubPacket(con, jid, Type.SET, request);
+		return (Subscription)reply.getExtension(PubSubElementType.SUBSCRIPTION);
+	}
+
+	/**
+	 * Remove the subscription related to the specified JID.  This will only 
+	 * work if there is only 1 subscription.  If there are multiple subscriptions,
+	 * use {@link #unsubscribe(String, String)}.
+	 * 
+	 * @param jid The JID used to subscribe to the node
+	 * 
+	 * @throws XMPPException
+	 */
+	public void unsubscribe(String jid)
+		throws XMPPException
+	{
+		unsubscribe(jid, null);
+	}
+	
+	/**
+	 * Remove the specific subscription related to the specified JID.
+	 * 
+	 * @param jid The JID used to subscribe to the node
+	 * @param subscriptionId The id of the subscription being removed
+	 * 
+	 * @throws XMPPException
+	 */
+	public void unsubscribe(String jid, String subscriptionId)
+		throws XMPPException
+	{
+		sendPubsubPacket(Type.SET, new UnsubscribeExtension(jid, getId(), subscriptionId));
+	}
+
+	/**
+	 * Returns a SubscribeForm for subscriptions, from which you can create an answer form to be submitted
+	 * via the {@link #sendConfigurationForm(Form)}.
+	 * 
+	 * @return A subscription options form
+	 * 
+	 * @throws XMPPException
+	 */
+	public SubscribeForm getSubscriptionOptions(String jid)
+		throws XMPPException
+	{
+		return getSubscriptionOptions(jid, null);
+	}
+
+
+	/**
+	 * Get the options for configuring the specified subscription.
+	 * 
+	 * @param jid JID the subscription is registered under
+	 * @param subscriptionId The subscription id
+	 * 
+	 * @return The subscription option form
+	 * 
+	 * @throws XMPPException
+	 */
+	public SubscribeForm getSubscriptionOptions(String jid, String subscriptionId)
+		throws XMPPException
+	{
+		PubSub packet = (PubSub)sendPubsubPacket(Type.GET, new OptionsExtension(jid, getId(), subscriptionId));
+		FormNode ext = (FormNode)packet.getExtension(PubSubElementType.OPTIONS);
+		return new SubscribeForm(ext.getForm());
+	}
+
+	/**
+	 * Register a listener for item publication events.  This 
+	 * listener will get called whenever an item is published to 
+	 * this node.
+	 * 
+	 * @param listener The handler for the event
+	 */
+	public void addItemEventListener(ItemEventListener listener)
+	{
+		PacketListener conListener = new ItemEventTranslator(listener); 
+		itemEventToListenerMap.put(listener, conListener);
+		con.addPacketListener(conListener, new EventContentFilter(EventElementType.items.toString(), "item"));
+	}
+
+	/**
+	 * Unregister a listener for publication events.
+	 * 
+	 * @param listener The handler to unregister
+	 */
+	public void removeItemEventListener(ItemEventListener listener)
+	{
+		PacketListener conListener = itemEventToListenerMap.remove(listener);
+		
+		if (conListener != null)
+			con.removePacketListener(conListener);
+	}
+
+	/**
+	 * Register a listener for configuration events.  This listener
+	 * will get called whenever the node's configuration changes.
+	 * 
+	 * @param listener The handler for the event
+	 */
+	public void addConfigurationListener(NodeConfigListener listener)
+	{
+		PacketListener conListener = new NodeConfigTranslator(listener); 
+		configEventToListenerMap.put(listener, conListener);
+		con.addPacketListener(conListener, new EventContentFilter(EventElementType.configuration.toString()));
+	}
+
+	/**
+	 * Unregister a listener for configuration events.
+	 * 
+	 * @param listener The handler to unregister
+	 */
+	public void removeConfigurationListener(NodeConfigListener listener)
+	{
+		PacketListener conListener = configEventToListenerMap .remove(listener);
+		
+		if (conListener != null)
+			con.removePacketListener(conListener);
+	}
+	
+	/**
+	 * Register an listener for item delete events.  This listener
+	 * gets called whenever an item is deleted from the node.
+	 * 
+	 * @param listener The handler for the event
+	 */
+	public void addItemDeleteListener(ItemDeleteListener listener)
+	{
+		PacketListener delListener = new ItemDeleteTranslator(listener); 
+		itemDeleteToListenerMap.put(listener, delListener);
+		EventContentFilter deleteItem = new EventContentFilter(EventElementType.items.toString(), "retract");
+		EventContentFilter purge = new EventContentFilter(EventElementType.purge.toString());
+		
+		con.addPacketListener(delListener, new OrFilter(deleteItem, purge));
+	}
+
+	/**
+	 * Unregister a listener for item delete events.
+	 * 
+	 * @param listener The handler to unregister
+	 */
+	public void removeItemDeleteListener(ItemDeleteListener listener)
+	{
+		PacketListener conListener = itemDeleteToListenerMap .remove(listener);
+		
+		if (conListener != null)
+			con.removePacketListener(conListener);
+	}
+
+	@Override
+	public String toString()
+	{
+		return super.toString() + " " + getClass().getName() + " id: " + id;
+	}
+	
+	protected PubSub createPubsubPacket(Type type, PacketExtension ext)
+	{
+		return createPubsubPacket(type, ext, null);
+	}
+	
+	protected PubSub createPubsubPacket(Type type, PacketExtension ext, PubSubNamespace ns)
+	{
+		return PubSubManager.createPubsubPacket(to, type, ext, ns);
+	}
+
+	protected Packet sendPubsubPacket(Type type, NodeExtension ext)
+		throws XMPPException
+	{
+		return PubSubManager.sendPubsubPacket(con, to, type, ext);
+	}
+
+	protected Packet sendPubsubPacket(Type type, NodeExtension ext, PubSubNamespace ns)
+		throws XMPPException
+	{
+		return PubSubManager.sendPubsubPacket(con, to, type, ext, ns);
+	}
+
+
+	private static List<String> getSubscriptionIds(Packet packet)
+	{
+		HeadersExtension headers = (HeadersExtension)packet.getExtension("headers", "http://jabber.org/protocol/shim");
+		List<String> values = null;
+		
+		if (headers != null)
+		{
+			values = new ArrayList<String>(headers.getHeaders().size());
+			
+			for (Header header : headers.getHeaders())
+			{
+				values.add(header.getValue());
+			}
+		}
+		return values;
+	}
+
+	/**
+	 * This class translates low level item publication events into api level objects for 
+	 * user consumption.
+	 * 
+	 * @author Robin Collier
+	 */
+	public class ItemEventTranslator implements PacketListener
+	{
+		private ItemEventListener listener;
+
+		public ItemEventTranslator(ItemEventListener eventListener)
+		{
+			listener = eventListener;
+		}
+		
+		public void processPacket(Packet packet)
+		{
+	        EventElement event = (EventElement)packet.getExtension("event", PubSubNamespace.EVENT.getXmlns());
+			ItemsExtension itemsElem = (ItemsExtension)event.getEvent();
+			DelayInformation delay = (DelayInformation)packet.getExtension("delay", "urn:xmpp:delay");
+			
+			// If there was no delay based on XEP-0203, then try XEP-0091 for backward compatibility
+			if (delay == null)
+			{
+				delay = (DelayInformation)packet.getExtension("x", "jabber:x:delay");
+			}
+			ItemPublishEvent eventItems = new ItemPublishEvent(itemsElem.getNode(), (List<Item>)itemsElem.getItems(), getSubscriptionIds(packet), (delay == null ? null : delay.getStamp()));
+			listener.handlePublishedItems(eventItems);
+		}
+	}
+
+	/**
+	 * This class translates low level item deletion events into api level objects for 
+	 * user consumption.
+	 * 
+	 * @author Robin Collier
+	 */
+	public class ItemDeleteTranslator implements PacketListener
+	{
+		private ItemDeleteListener listener;
+
+		public ItemDeleteTranslator(ItemDeleteListener eventListener)
+		{
+			listener = eventListener;
+		}
+		
+		public void processPacket(Packet packet)
+		{
+	        EventElement event = (EventElement)packet.getExtension("event", PubSubNamespace.EVENT.getXmlns());
+	        
+	        List<PacketExtension> extList = event.getExtensions();
+	        
+	        if (extList.get(0).getElementName().equals(PubSubElementType.PURGE_EVENT.getElementName()))
+	        {
+	        	listener.handlePurge();
+	        }
+	        else
+	        {
+				ItemsExtension itemsElem = (ItemsExtension)event.getEvent();
+				Collection<? extends PacketExtension> pubItems = itemsElem.getItems();
+				Iterator<RetractItem> it = (Iterator<RetractItem>)pubItems.iterator();
+				List<String> items = new ArrayList<String>(pubItems.size());
+
+				while (it.hasNext())
+				{
+					RetractItem item = it.next();
+					items.add(item.getId());
+				}
+
+				ItemDeleteEvent eventItems = new ItemDeleteEvent(itemsElem.getNode(), items, getSubscriptionIds(packet));
+				listener.handleDeletedItems(eventItems);
+	        }
+		}
+	}
+	
+	/**
+	 * This class translates low level node configuration events into api level objects for 
+	 * user consumption.
+	 * 
+	 * @author Robin Collier
+	 */
+	public class NodeConfigTranslator implements PacketListener
+	{
+		private NodeConfigListener listener;
+
+		public NodeConfigTranslator(NodeConfigListener eventListener)
+		{
+			listener = eventListener;
+		}
+		
+		public void processPacket(Packet packet)
+		{
+	        EventElement event = (EventElement)packet.getExtension("event", PubSubNamespace.EVENT.getXmlns());
+			ConfigurationEvent config = (ConfigurationEvent)event.getEvent();
+
+			listener.handleNodeConfiguration(config);
+		}
+	}
+
+	/**
+	 * Filter for {@link PacketListener} to filter out events not specific to the 
+	 * event type expected for this node.
+	 * 
+	 * @author Robin Collier
+	 */
+	class EventContentFilter implements PacketFilter
+	{
+		private String firstElement;
+		private String secondElement;
+		
+		EventContentFilter(String elementName)
+		{
+			firstElement = elementName;
+		}
+
+		EventContentFilter(String firstLevelEelement, String secondLevelElement)
+		{
+			firstElement = firstLevelEelement;
+			secondElement = secondLevelElement;
+		}
+
+		public boolean accept(Packet packet)
+		{
+			if (!(packet instanceof Message))
+				return false;
+
+			EventElement event = (EventElement)packet.getExtension("event", PubSubNamespace.EVENT.getXmlns());
+			
+			if (event == null)
+				return false;
+
+			NodeExtension embedEvent = event.getEvent();
+			
+			if (embedEvent == null)
+				return false;
+			
+			if (embedEvent.getElementName().equals(firstElement))
+			{
+				if (!embedEvent.getNode().equals(getId()))
+					return false;
+				
+				if (secondElement == null)
+					return true;
+				
+				if (embedEvent instanceof EmbeddedPacketExtension)
+				{
+					List<PacketExtension> secondLevelList = ((EmbeddedPacketExtension)embedEvent).getExtensions();
+					
+					if (secondLevelList.size() > 0 && secondLevelList.get(0).getElementName().equals(secondElement))
+						return true;
+				}
+			}
+			return false;
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/NodeEvent.java b/src/org/jivesoftware/smackx/pubsub/NodeEvent.java
new file mode 100644
index 0000000..1392e85
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/NodeEvent.java
@@ -0,0 +1,35 @@
+/**
+ * $RCSfile$
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2009 Robin Collier.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+abstract public class NodeEvent
+{
+	private String nodeId;
+	
+	protected NodeEvent(String id)
+	{
+		nodeId = id;
+	}
+	
+	public String getNodeId()
+	{
+		return nodeId;
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/NodeExtension.java b/src/org/jivesoftware/smackx/pubsub/NodeExtension.java
new file mode 100644
index 0000000..7e4cdec
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/NodeExtension.java
@@ -0,0 +1,85 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * A class which represents a common element within the pubsub defined
+ * schemas.  One which has a <b>node</b> as an attribute.  This class is 
+ * used on its own as well as a base class for many others, since the 
+ * node is a central concept to most pubsub functionality.
+ * 
+ * @author Robin Collier
+ */
+public class NodeExtension implements PacketExtension
+{
+	private PubSubElementType element;
+	private String node;
+	
+	/**
+	 * Constructs a <tt>NodeExtension</tt> with an element name specified
+	 * by {@link PubSubElementType} and the specified node id.
+	 * 
+	 * @param elem Defines the element name and namespace
+	 * @param nodeId Specifies the id of the node
+	 */
+	public NodeExtension(PubSubElementType elem, String nodeId)
+	{
+		element = elem;
+		this.node = nodeId;
+	}
+
+	/**
+	 * Constructs a <tt>NodeExtension</tt> with an element name specified
+	 * by {@link PubSubElementType}.
+	 * 
+	 * @param elem Defines the element name and namespace
+	 */
+	public NodeExtension(PubSubElementType elem)
+	{
+		this(elem, null);
+	}
+
+	/**
+	 * Gets the node id
+	 * 
+	 * @return The node id
+	 */
+	public String getNode()
+	{
+		return node;
+	}
+	
+	public String getElementName()
+	{
+		return element.getElementName();
+	}
+
+	public String getNamespace()
+	{
+		return element.getNamespace().getXmlns();
+	}
+
+	public String toXML()
+	{
+		return '<' + getElementName() + (node == null ? "" : " node='" + node + '\'') + "/>";
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + " - content [" + toXML() + "]";
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/NodeType.java b/src/org/jivesoftware/smackx/pubsub/NodeType.java
new file mode 100644
index 0000000..5ee5a05
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/NodeType.java
@@ -0,0 +1,25 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * Defines the available types of nodes
+ * 
+ * @author Robin Collier
+ */
+public enum NodeType
+{
+	leaf,
+	collection;
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/OptionsExtension.java b/src/org/jivesoftware/smackx/pubsub/OptionsExtension.java
new file mode 100644
index 0000000..32c0331
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/OptionsExtension.java
@@ -0,0 +1,72 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.pubsub.util.XmlUtils;
+
+/**
+ * A packet extension representing the <b>options</b> element. 
+ * 
+ * @author Robin Collier
+ */
+public class OptionsExtension extends NodeExtension
+{
+	protected String jid;
+	protected String id;
+	
+	public OptionsExtension(String subscriptionJid)
+	{
+		this(subscriptionJid, null, null);
+	}
+	
+	public OptionsExtension(String subscriptionJid, String nodeId)
+	{
+		this(subscriptionJid, nodeId, null);
+	}
+	
+	public OptionsExtension(String jid, String nodeId, String subscriptionId)
+	{
+		super(PubSubElementType.OPTIONS, nodeId);
+		this.jid = jid;
+		id = subscriptionId;
+	}
+	
+	public String getJid()
+	{
+		return jid;
+	}
+	
+	public String getId()
+	{
+		return id;
+	}
+	
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		XmlUtils.appendAttribute(builder, "jid", jid);
+		
+		if (getNode() != null)
+			XmlUtils.appendAttribute(builder, "node", getNode());
+		
+		if (id != null)
+			XmlUtils.appendAttribute(builder, "subid", id);
+		
+		builder.append("/>");
+		return builder.toString();
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PayloadItem.java b/src/org/jivesoftware/smackx/pubsub/PayloadItem.java
new file mode 100644
index 0000000..488fd97
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PayloadItem.java
@@ -0,0 +1,138 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.pubsub.provider.ItemProvider;
+
+/**
+ * This class represents an item that has been, or will be published to a
+ * pubsub node.  An <tt>Item</tt> has several properties that are dependent
+ * on the configuration of the node to which it has been or will be published.
+ * 
+ * <h1>An Item received from a node (via {@link LeafNode#getItems()} or {@link LeafNode#addItemEventListener(org.jivesoftware.smackx.pubsub.listener.ItemEventListener)}</b>
+ * <li>Will always have an id (either user or server generated) unless node configuration has both
+ * {@link ConfigureForm#isPersistItems()} and {@link ConfigureForm#isDeliverPayloads()}set to false.
+ * <li>Will have a payload if the node configuration has {@link ConfigureForm#isDeliverPayloads()} set 
+ * to true, otherwise it will be null.
+ * 
+ * <h1>An Item created to send to a node (via {@link LeafNode#send()} or {@link LeafNode#publish()}</b>
+ * <li>The id is optional, since the server will generate one if necessary, but should be used if it is 
+ * meaningful in the context of the node.  This value must be unique within the node that it is sent to, since
+ * resending an item with the same id will overwrite the one that already exists if the items are persisted.
+ * <li>Will require payload if the node configuration has {@link ConfigureForm#isDeliverPayloads()} set
+ * to true. 
+ * 
+ * <p>To customise the payload object being returned from the {@link #getPayload()} method, you can
+ * add a custom parser as explained in {@link ItemProvider}.
+ * 
+ * @author Robin Collier
+ */
+public class PayloadItem<E extends PacketExtension> extends Item
+{
+	private E payload;
+	
+	/**
+	 * Create an <tt>Item</tt> with no id and a payload  The id will be set by the server.  
+	 * 
+	 * @param payloadExt A {@link PacketExtension} which represents the payload data.
+	 */
+	public PayloadItem(E payloadExt)
+	{
+		super();
+		
+		if (payloadExt == null)
+			throw new IllegalArgumentException("payload cannot be 'null'");
+		payload = payloadExt;
+	}
+
+	/**
+	 * Create an <tt>Item</tt> with an id and payload.  
+	 * 
+	 * @param itemId The id of this item.  It can be null if we want the server to set the id.
+	 * @param payloadExt A {@link PacketExtension} which represents the payload data.
+	 */
+	public PayloadItem(String itemId, E payloadExt)
+	{
+		super(itemId);
+		
+		if (payloadExt == null)
+			throw new IllegalArgumentException("payload cannot be 'null'");
+		payload = payloadExt;
+	}
+	
+	/**
+	 * Create an <tt>Item</tt> with an id, node id and payload.  
+	 * 
+	 * <p>
+	 * <b>Note:</b> This is not valid for publishing an item to a node, only receiving from 
+	 * one as part of {@link Message}.  If used to create an Item to publish 
+	 * (via {@link LeafNode#publish(Item)}, the server <i>may</i> return an
+	 * error for an invalid packet.
+	 * 
+	 * @param itemId The id of this item.
+	 * @param nodeId The id of the node the item was published to.
+	 * @param payloadExt A {@link PacketExtension} which represents the payload data.
+	 */
+	public PayloadItem(String itemId, String nodeId, E payloadExt)
+	{
+		super(itemId, nodeId);
+		
+		if (payloadExt == null)
+			throw new IllegalArgumentException("payload cannot be 'null'");
+		payload = payloadExt;
+	}
+	
+	/**
+	 * Get the payload associated with this <tt>Item</tt>.  Customising the payload
+	 * parsing from the server can be accomplished as described in {@link ItemProvider}.
+	 * 
+	 * @return The payload as a {@link PacketExtension}.
+	 */
+	public E getPayload()
+	{
+		return payload;
+	}
+	
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<item");
+		
+		if (getId() != null)
+		{
+			builder.append(" id='");
+			builder.append(getId());
+			builder.append("'");
+		}
+		
+        if (getNode() != null) {
+            builder.append(" node='");
+            builder.append(getNode());
+            builder.append("'");
+        }
+		builder.append(">");
+		builder.append(payload.toXML());
+		builder.append("</item>");
+		
+		return builder.toString();
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + " | Content [" + toXML() + "]";
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PresenceState.java b/src/org/jivesoftware/smackx/pubsub/PresenceState.java
new file mode 100644
index 0000000..0612fc2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PresenceState.java
@@ -0,0 +1,25 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/** 
+ * Defines the possible valid presence states for node subscription via
+ * {@link SubscribeForm#getShowValues()}.
+ * 
+ * @author Robin Collier
+ */
+public enum PresenceState
+{
+	chat, online, away, xa, dnd
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PubSubElementType.java b/src/org/jivesoftware/smackx/pubsub/PubSubElementType.java
new file mode 100644
index 0000000..a887ca2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PubSubElementType.java
@@ -0,0 +1,80 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+
+/**
+ * Defines all the possible element types as defined for all the pubsub
+ * schemas in all 3 namespaces.
+ * 
+ * @author Robin Collier
+ */
+public enum PubSubElementType
+{
+	CREATE("create", PubSubNamespace.BASIC),
+	DELETE("delete", PubSubNamespace.OWNER),
+	DELETE_EVENT("delete", PubSubNamespace.EVENT),
+	CONFIGURE("configure", PubSubNamespace.BASIC),
+	CONFIGURE_OWNER("configure", PubSubNamespace.OWNER),
+	CONFIGURATION("configuration", PubSubNamespace.EVENT),
+	OPTIONS("options", PubSubNamespace.BASIC),
+	DEFAULT("default", PubSubNamespace.OWNER),	
+	ITEMS("items", PubSubNamespace.BASIC),
+	ITEMS_EVENT("items", PubSubNamespace.EVENT),
+	ITEM("item", PubSubNamespace.BASIC),
+	ITEM_EVENT("item", PubSubNamespace.EVENT),
+	PUBLISH("publish", PubSubNamespace.BASIC),
+	PUBLISH_OPTIONS("publish-options", PubSubNamespace.BASIC), 
+	PURGE_OWNER("purge", PubSubNamespace.OWNER),
+	PURGE_EVENT("purge", PubSubNamespace.EVENT),
+	RETRACT("retract", PubSubNamespace.BASIC), 
+	AFFILIATIONS("affiliations", PubSubNamespace.BASIC), 
+	SUBSCRIBE("subscribe", PubSubNamespace.BASIC), 
+	SUBSCRIPTION("subscription", PubSubNamespace.BASIC),
+	SUBSCRIPTIONS("subscriptions", PubSubNamespace.BASIC), 
+	UNSUBSCRIBE("unsubscribe", PubSubNamespace.BASIC);
+
+	private String eName;
+	private PubSubNamespace nSpace;
+	
+	private PubSubElementType(String elemName, PubSubNamespace ns)
+	{
+		eName = elemName;
+		nSpace = ns;
+	}
+	
+	public PubSubNamespace getNamespace()
+	{
+		return nSpace;
+	}
+	
+	public String getElementName()
+	{
+		return eName;
+	}
+	
+	public static PubSubElementType valueOfFromElemName(String elemName, String namespace)
+	{
+		int index = namespace.lastIndexOf('#');
+		String fragment = (index == -1 ? null : namespace.substring(index+1));
+		
+		if (fragment != null)
+		{
+			return valueOf((elemName + '_' + fragment).toUpperCase());
+		}
+		return valueOf(elemName.toUpperCase().replace('-', '_'));
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PubSubManager.java b/src/org/jivesoftware/smackx/pubsub/PubSubManager.java
new file mode 100644
index 0000000..4fb0158
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PubSubManager.java
@@ -0,0 +1,329 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.packet.IQ.Type;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+import org.jivesoftware.smackx.pubsub.packet.PubSub;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+import org.jivesoftware.smackx.pubsub.packet.SyncPacketSend;
+import org.jivesoftware.smackx.pubsub.util.NodeUtils;
+
+/**
+ * This is the starting point for access to the pubsub service.  It
+ * will provide access to general information about the service, as
+ * well as create or retrieve pubsub {@link LeafNode} instances.  These 
+ * instances provide the bulk of the functionality as defined in the 
+ * pubsub specification <a href="http://xmpp.org/extensions/xep-0060.html">XEP-0060</a>.
+ * 
+ * @author Robin Collier
+ */
+final public class PubSubManager
+{
+	private Connection con;
+	private String to;
+	private Map<String, Node> nodeMap = new ConcurrentHashMap<String, Node>();
+	
+	/**
+	 * Create a pubsub manager associated to the specified connection.  Defaults the service
+	 * name to <i>pubsub</i>
+	 * 
+	 * @param connection The XMPP connection
+	 */
+	public PubSubManager(Connection connection)
+	{
+		con = connection;
+		to = "pubsub." + connection.getServiceName();
+	}
+	
+	/**
+	 * Create a pubsub manager associated to the specified connection where
+	 * the pubsub requests require a specific to address for packets.
+	 * 
+	 * @param connection The XMPP connection
+	 * @param toAddress The pubsub specific to address (required for some servers)
+	 */
+	public PubSubManager(Connection connection, String toAddress)
+	{
+		con = connection;
+		to = toAddress;
+	}
+	
+	/**
+	 * Creates an instant node, if supported.
+	 * 
+	 * @return The node that was created
+	 * @exception XMPPException
+	 */
+	public LeafNode createNode()
+		throws XMPPException
+	{
+		PubSub reply = (PubSub)sendPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.CREATE));
+		NodeExtension elem = (NodeExtension)reply.getExtension("create", PubSubNamespace.BASIC.getXmlns());
+		
+		LeafNode newNode = new LeafNode(con, elem.getNode());
+		newNode.setTo(to);
+		nodeMap.put(newNode.getId(), newNode);
+		
+		return newNode;
+	}
+	
+	/**
+	 * Creates a node with default configuration.
+	 * 
+	 * @param id The id of the node, which must be unique within the 
+	 * pubsub service
+	 * @return The node that was created
+	 * @exception XMPPException
+	 */
+	public LeafNode createNode(String id)
+		throws XMPPException
+	{
+		return (LeafNode)createNode(id, null);
+	}
+	
+	/**
+	 * Creates a node with specified configuration.
+	 * 
+	 * Note: This is the only way to create a collection node.
+	 * 
+	 * @param name The name of the node, which must be unique within the 
+	 * pubsub service
+	 * @param config The configuration for the node
+	 * @return The node that was created
+	 * @exception XMPPException
+	 */
+	public Node createNode(String name, Form config)
+		throws XMPPException
+	{
+		PubSub request = createPubsubPacket(to, Type.SET, new NodeExtension(PubSubElementType.CREATE, name));
+		boolean isLeafNode = true;
+		
+		if (config != null)
+		{
+			request.addExtension(new FormNode(FormNodeType.CONFIGURE, config));
+			FormField nodeTypeField = config.getField(ConfigureNodeFields.node_type.getFieldName());
+			
+			if (nodeTypeField != null)
+				isLeafNode = nodeTypeField.getValues().next().equals(NodeType.leaf.toString());
+		}
+
+		// Errors will cause exceptions in getReply, so it only returns
+		// on success.
+		sendPubsubPacket(con, to, Type.SET, request);
+		Node newNode = isLeafNode ? new LeafNode(con, name) : new CollectionNode(con, name);
+		newNode.setTo(to);
+		nodeMap.put(newNode.getId(), newNode);
+		
+		return newNode;
+	}
+
+	/**
+	 * Retrieves the requested node, if it exists.  It will throw an 
+	 * exception if it does not.
+	 * 
+	 * @param id - The unique id of the node
+	 * @return the node
+	 * @throws XMPPException The node does not exist
+	 */
+	public <T extends Node> T getNode(String id)
+		throws XMPPException
+	{
+		Node node = nodeMap.get(id);
+		
+		if (node == null)
+		{
+			DiscoverInfo info = new DiscoverInfo();
+			info.setTo(to);
+			info.setNode(id);
+			
+			DiscoverInfo infoReply = (DiscoverInfo)SyncPacketSend.getReply(con, info);
+			
+			if (infoReply.getIdentities().next().getType().equals(NodeType.leaf.toString()))
+				node = new LeafNode(con, id);
+			else
+				node = new CollectionNode(con, id);
+			node.setTo(to);
+			nodeMap.put(id, node);
+		}
+		return (T) node;
+	}
+	
+	/**
+	 * Get all the nodes that currently exist as a child of the specified
+	 * collection node.  If the service does not support collection nodes
+	 * then all nodes will be returned.
+	 * 
+	 * To retrieve contents of the root collection node (if it exists), 
+	 * or there is no root collection node, pass null as the nodeId.
+	 * 
+	 * @param nodeId - The id of the collection node for which the child 
+	 * nodes will be returned.  
+	 * @return {@link DiscoverItems} representing the existing nodes
+	 * 
+	 * @throws XMPPException
+	 */
+	public DiscoverItems discoverNodes(String nodeId)
+		throws XMPPException
+	{
+		DiscoverItems items = new DiscoverItems();
+		
+		if (nodeId != null)
+			items.setNode(nodeId);
+		items.setTo(to);
+		DiscoverItems nodeItems = (DiscoverItems)SyncPacketSend.getReply(con, items);
+		return nodeItems;
+	}
+	
+	/**
+	 * Gets the subscriptions on the root node.
+	 * 
+	 * @return List of exceptions
+	 * 
+	 * @throws XMPPException
+	 */
+	public List<Subscription> getSubscriptions()
+		throws XMPPException
+	{
+		Packet reply = sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.SUBSCRIPTIONS));
+		SubscriptionsExtension subElem = (SubscriptionsExtension)reply.getExtension(PubSubElementType.SUBSCRIPTIONS.getElementName(), PubSubElementType.SUBSCRIPTIONS.getNamespace().getXmlns());
+		return subElem.getSubscriptions();
+	}
+	
+	/**
+	 * Gets the affiliations on the root node.
+	 * 
+	 * @return List of affiliations
+	 * 
+	 * @throws XMPPException
+	 */
+	public List<Affiliation> getAffiliations()
+		throws XMPPException
+	{
+		PubSub reply = (PubSub)sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.AFFILIATIONS));
+		AffiliationsExtension listElem = (AffiliationsExtension)reply.getExtension(PubSubElementType.AFFILIATIONS);
+		return listElem.getAffiliations();
+	}
+
+	/**
+	 * Delete the specified node
+	 * 
+	 * @param nodeId
+	 * @throws XMPPException
+	 */
+	public void deleteNode(String nodeId)
+		throws XMPPException
+	{
+		sendPubsubPacket(Type.SET, new NodeExtension(PubSubElementType.DELETE, nodeId), PubSubElementType.DELETE.getNamespace());
+		nodeMap.remove(nodeId);
+	}
+	
+	/**
+	 * Returns the default settings for Node configuration.
+	 * 
+	 * @return configuration form containing the default settings.
+	 */
+	public ConfigureForm getDefaultConfiguration()
+		throws XMPPException
+	{
+		// Errors will cause exceptions in getReply, so it only returns
+		// on success.
+		PubSub reply = (PubSub)sendPubsubPacket(Type.GET, new NodeExtension(PubSubElementType.DEFAULT), PubSubElementType.DEFAULT.getNamespace());
+		return NodeUtils.getFormFromPacket(reply, PubSubElementType.DEFAULT);
+	}
+	
+	/**
+	 * Gets the supported features of the servers pubsub implementation
+	 * as a standard {@link DiscoverInfo} instance.
+	 * 
+	 * @return The supported features
+	 * 
+	 * @throws XMPPException
+	 */
+	public DiscoverInfo getSupportedFeatures()
+		throws XMPPException
+	{
+		ServiceDiscoveryManager mgr = ServiceDiscoveryManager.getInstanceFor(con);
+		return mgr.discoverInfo(to);
+	}
+	
+	private Packet sendPubsubPacket(Type type, PacketExtension ext, PubSubNamespace ns)
+		throws XMPPException
+	{
+		return sendPubsubPacket(con, to, type, ext, ns);
+	}
+
+	private Packet sendPubsubPacket(Type type, PacketExtension ext)
+		throws XMPPException
+	{
+		return sendPubsubPacket(type, ext, null);
+	}
+
+	static PubSub createPubsubPacket(String to, Type type, PacketExtension ext)
+	{
+		return createPubsubPacket(to, type, ext, null);
+	}
+	
+	static PubSub createPubsubPacket(String to, Type type, PacketExtension ext, PubSubNamespace ns)
+	{
+		PubSub request = new PubSub();
+		request.setTo(to);
+		request.setType(type);
+		
+		if (ns != null)
+		{
+			request.setPubSubNamespace(ns);
+		}
+		request.addExtension(ext);
+		
+		return request;
+	}
+
+	static Packet sendPubsubPacket(Connection con, String to, Type type, PacketExtension ext)
+		throws XMPPException
+	{
+		return sendPubsubPacket(con, to, type, ext, null);
+	}
+	
+	static Packet sendPubsubPacket(Connection con, String to, Type type, PacketExtension ext, PubSubNamespace ns)
+		throws XMPPException
+	{
+		return SyncPacketSend.getReply(con, createPubsubPacket(to, type, ext, ns));
+	}
+
+	static Packet sendPubsubPacket(Connection con, String to, Type type, PubSub packet)
+		throws XMPPException
+	{
+		return sendPubsubPacket(con, to, type, packet, null);
+	}
+
+	static Packet sendPubsubPacket(Connection con, String to, Type type, PubSub packet, PubSubNamespace ns)
+		throws XMPPException
+	{
+		return SyncPacketSend.getReply(con, packet);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PublishItem.java b/src/org/jivesoftware/smackx/pubsub/PublishItem.java
new file mode 100644
index 0000000..ffbd705
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PublishItem.java
@@ -0,0 +1,70 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.ArrayList;
+import java.util.Collection;
+
+/**
+ * Represents a request to publish an item(s) to a specific node.
+ * 
+ * @author Robin Collier
+ */
+public class PublishItem <T extends Item> extends NodeExtension
+{
+	protected Collection<T> items;
+	
+	/**
+	 * Construct a request to publish an item to a node.
+	 * 
+	 * @param nodeId The node to publish to
+	 * @param toPublish The {@link Item} to publish
+	 */
+	public PublishItem(String nodeId, T toPublish)
+	{
+		super(PubSubElementType.PUBLISH, nodeId);
+		items = new ArrayList<T>(1);
+		items.add(toPublish);
+	}
+
+	/**
+	 * Construct a request to publish multiple items to a node.
+	 * 
+	 * @param nodeId The node to publish to
+	 * @param toPublish The list of {@link Item} to publish
+	 */
+	public PublishItem(String nodeId, Collection<T> toPublish)
+	{
+		super(PubSubElementType.PUBLISH, nodeId);
+		items = toPublish;
+	}
+
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		builder.append(" node='");
+		builder.append(getNode());
+		builder.append("'>");
+		
+		for (Item item : items)
+		{
+			builder.append(item.toXML());
+		}
+		builder.append("</publish>");
+		
+		return builder.toString();
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/PublishModel.java b/src/org/jivesoftware/smackx/pubsub/PublishModel.java
new file mode 100644
index 0000000..4b5a851
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/PublishModel.java
@@ -0,0 +1,32 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * Determines who may publish to a node.  Denotes possible values 
+ * for {@link ConfigureForm#setPublishModel(PublishModel)}.
+ * 
+ * @author Robin Collier
+ */
+public enum PublishModel
+{
+	/** Only publishers may publish */
+	publishers,
+	
+	/** Only subscribers may publish */
+	subscribers,
+	
+	/** Anyone may publish */
+	open;
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/RetractItem.java b/src/org/jivesoftware/smackx/pubsub/RetractItem.java
new file mode 100644
index 0000000..97db5cc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/RetractItem.java
@@ -0,0 +1,59 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+
+/**
+ * Represents and item that has been deleted from a node.
+ * 
+ * @author Robin Collier
+ */
+public class RetractItem implements PacketExtension
+{
+	private String id;
+
+	/**
+	 * Construct a <tt>RetractItem</tt> with the specified id.
+	 * 
+	 * @param itemId The id if the item deleted
+	 */
+	public RetractItem(String itemId)
+	{
+		if (itemId == null)
+			throw new IllegalArgumentException("itemId must not be 'null'");
+		id = itemId;
+	}
+	
+	public String getId()
+	{
+		return id;
+	}
+
+	public String getElementName()
+	{
+		return "retract";
+	}
+
+	public String getNamespace()
+	{
+		return PubSubNamespace.EVENT.getXmlns();
+	}
+
+	public String toXML()
+	{
+		return "<retract id='" + id + "'/>";
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SimplePayload.java b/src/org/jivesoftware/smackx/pubsub/SimplePayload.java
new file mode 100644
index 0000000..9d114b0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SimplePayload.java
@@ -0,0 +1,65 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * The default payload representation for {@link Item#getPayload()}.  It simply 
+ * stores the XML payload as a string.
+ *  
+ * @author Robin Collier
+ */
+public class SimplePayload implements PacketExtension
+{
+	private String elemName;
+	private String ns;
+	private String payload;
+	
+	/**
+	 * Construct a <tt>SimplePayload</tt> object with the specified element name, 
+	 * namespace and content.  The content must be well formed XML.
+	 * 
+	 * @param elementName The root element name (of the payload)
+	 * @param namespace The namespace of the payload, null if there is none
+	 * @param xmlPayload The payload data
+	 */
+	public SimplePayload(String elementName, String namespace, String xmlPayload)
+	{
+		elemName = elementName;
+		payload = xmlPayload;
+		ns = namespace;
+	}
+
+	public String getElementName()
+	{
+		return elemName;
+	}
+
+	public String getNamespace()
+	{
+		return ns;
+	}
+
+	public String toXML()
+	{
+		return payload;
+	}
+
+	@Override
+	public String toString()
+	{
+		return getClass().getName() + "payload [" + toXML() + "]";
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SubscribeExtension.java b/src/org/jivesoftware/smackx/pubsub/SubscribeExtension.java
new file mode 100644
index 0000000..daf8db7
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SubscribeExtension.java
@@ -0,0 +1,60 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * Represents a request to subscribe to a node.
+ * 
+ * @author Robin Collier
+ */
+public class SubscribeExtension extends NodeExtension
+{
+	protected String jid;
+	
+	public SubscribeExtension(String subscribeJid)
+	{
+		super(PubSubElementType.SUBSCRIBE);
+		jid = subscribeJid;
+	}
+	
+	public SubscribeExtension(String subscribeJid, String nodeId)
+	{
+		super(PubSubElementType.SUBSCRIBE, nodeId);
+		jid = subscribeJid;
+	}
+
+	public String getJid()
+	{
+		return jid;
+	}
+
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		
+		if (getNode() != null)
+		{
+			builder.append(" node='");
+			builder.append(getNode());
+			builder.append("'");
+		}
+		builder.append(" jid='");
+		builder.append(getJid());
+		builder.append("'/>");
+		
+		return builder.toString();
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SubscribeForm.java b/src/org/jivesoftware/smackx/pubsub/SubscribeForm.java
new file mode 100644
index 0000000..53f2606
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SubscribeForm.java
@@ -0,0 +1,241 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
+import java.util.Iterator;
+import java.util.UnknownFormatConversionException;
+
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.packet.DataForm;
+
+/**
+ * A decorator for a {@link Form} to easily enable reading and updating
+ * of subscription options.  All operations read or update the underlying {@link DataForm}.
+ * 
+ * <p>Unlike the {@link Form}.setAnswer(XXX)} methods, which throw an exception if the field does not
+ * exist, all <b>SubscribeForm.setXXX</b> methods will create the field in the wrapped form
+ * if it does not already exist.
+ * 
+ * @author Robin Collier
+ */
+public class SubscribeForm extends Form
+{	
+	public SubscribeForm(DataForm configDataForm)
+	{
+		super(configDataForm);
+	}
+	
+	public SubscribeForm(Form subscribeOptionsForm)
+	{
+		super(subscribeOptionsForm.getDataFormToSend());
+	}
+	
+	public SubscribeForm(FormType formType)
+	{
+		super(formType.toString());
+	}
+	
+	/**
+	 * Determines if an entity wants to receive notifications.
+	 * 
+	 * @return true if want to receive, false otherwise
+	 */
+	public boolean isDeliverOn()
+	{
+		return parseBoolean(getFieldValue(SubscribeOptionFields.deliver));
+	}
+	
+	/**
+	 * Sets whether an entity wants to receive notifications.
+	 *
+	 * @param deliverNotifications
+	 */
+	public void setDeliverOn(boolean deliverNotifications)
+	{
+		addField(SubscribeOptionFields.deliver, FormField.TYPE_BOOLEAN);
+		setAnswer(SubscribeOptionFields.deliver.getFieldName(), deliverNotifications);
+	}
+
+	/**
+	 * Determines if notifications should be delivered as aggregations or not.
+	 * 
+	 * @return true to aggregate, false otherwise
+	 */
+	public boolean isDigestOn()
+	{
+		return parseBoolean(getFieldValue(SubscribeOptionFields.digest));
+	}
+	
+	/**
+	 * Sets whether notifications should be delivered as aggregations or not.
+	 * 
+	 * @param digestOn true to aggregate, false otherwise 
+	 */
+	public void setDigestOn(boolean digestOn)
+	{
+		addField(SubscribeOptionFields.deliver, FormField.TYPE_BOOLEAN);
+		setAnswer(SubscribeOptionFields.deliver.getFieldName(), digestOn);
+	}
+
+	/**
+	 * Gets the minimum number of milliseconds between sending notification digests
+	 * 
+	 * @return The frequency in milliseconds
+	 */
+	public int getDigestFrequency()
+	{
+		return Integer.parseInt(getFieldValue(SubscribeOptionFields.digest_frequency));
+	}
+
+	/**
+	 * Sets the minimum number of milliseconds between sending notification digests
+	 * 
+	 * @param frequency The frequency in milliseconds
+	 */
+	public void setDigestFrequency(int frequency)
+	{
+		addField(SubscribeOptionFields.digest_frequency, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(SubscribeOptionFields.digest_frequency.getFieldName(), frequency);
+	}
+
+	/**
+	 * Get the time at which the leased subscription will expire, or has expired.
+	 * 
+	 * @return The expiry date
+	 */
+	public Date getExpiry()
+	{
+		String dateTime = getFieldValue(SubscribeOptionFields.expire);
+		try
+		{
+			return StringUtils.parseDate(dateTime);
+		}
+		catch (ParseException e)
+		{
+			UnknownFormatConversionException exc = new UnknownFormatConversionException(dateTime);
+			exc.initCause(e);
+			throw exc;
+		}
+	}
+	
+	/**
+	 * Sets the time at which the leased subscription will expire, or has expired.
+	 * 
+	 * @param expire The expiry date
+	 */
+	public void setExpiry(Date expire)
+	{
+		addField(SubscribeOptionFields.expire, FormField.TYPE_TEXT_SINGLE);
+		setAnswer(SubscribeOptionFields.expire.getFieldName(), StringUtils.formatXEP0082Date(expire));
+	}
+	
+	/**
+	 * Determines whether the entity wants to receive an XMPP message body in 
+	 * addition to the payload format.
+	 * 
+	 * @return true to receive the message body, false otherwise
+	 */
+	public boolean isIncludeBody()
+	{
+		return parseBoolean(getFieldValue(SubscribeOptionFields.include_body));
+	}
+	
+	/**
+	 * Sets whether the entity wants to receive an XMPP message body in 
+	 * addition to the payload format.
+	 * 
+	 * @param include true to receive the message body, false otherwise
+	 */
+	public void setIncludeBody(boolean include)
+	{
+		addField(SubscribeOptionFields.include_body, FormField.TYPE_BOOLEAN);
+		setAnswer(SubscribeOptionFields.include_body.getFieldName(), include);
+	}
+
+	/**
+	 * Gets the {@link PresenceState} for which an entity wants to receive 
+	 * notifications.
+	 * 
+	 * @return iterator over the list of states
+	 */
+	public Iterator<PresenceState> getShowValues()
+	{
+		ArrayList<PresenceState> result = new ArrayList<PresenceState>(5);
+		Iterator<String > it = getFieldValues(SubscribeOptionFields.show_values);
+		
+		while (it.hasNext())
+		{
+			String state = it.next();
+			result.add(PresenceState.valueOf(state));
+		}
+		return result.iterator();
+	}
+	
+	/**
+	 * Sets the list of {@link PresenceState} for which an entity wants
+	 * to receive notifications.
+	 * 
+	 * @param stateValues The list of states
+	 */
+	public void setShowValues(Collection<PresenceState> stateValues)
+	{
+		ArrayList<String> values = new ArrayList<String>(stateValues.size());
+		
+		for (PresenceState state : stateValues)
+		{
+			values.add(state.toString());
+		}
+		addField(SubscribeOptionFields.show_values, FormField.TYPE_LIST_MULTI);
+		setAnswer(SubscribeOptionFields.show_values.getFieldName(), values);
+	}
+	
+	
+	static private boolean parseBoolean(String fieldValue)
+	{
+		return ("1".equals(fieldValue) || "true".equals(fieldValue));
+	}
+
+	private String getFieldValue(SubscribeOptionFields field)
+	{
+		FormField formField = getField(field.getFieldName());
+		
+		return formField.getValues().next();
+	}
+
+	private Iterator<String> getFieldValues(SubscribeOptionFields field)
+	{
+		FormField formField = getField(field.getFieldName());
+		
+		return formField.getValues();
+	}
+
+	private void addField(SubscribeOptionFields nodeField, String type)
+	{
+		String fieldName = nodeField.getFieldName();
+		
+		if (getField(fieldName) == null)
+		{
+			FormField field = new FormField(fieldName);
+			field.setType(type);
+			addField(field);
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SubscribeOptionFields.java b/src/org/jivesoftware/smackx/pubsub/SubscribeOptionFields.java
new file mode 100644
index 0000000..dfca601
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SubscribeOptionFields.java
@@ -0,0 +1,99 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Calendar;
+
+/**
+ * Defines the possible field options for a subscribe options form as defined 
+ * by <a href="http://xmpp.org/extensions/xep-0060.html#registrar-formtypes-subscribe">Section 16.4.2</a>.
+ * 
+ * @author Robin Collier
+ */
+public enum SubscribeOptionFields
+{
+	/**
+	 * Whether an entity wants to receive or disable notifications
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	deliver,
+
+	/**
+	 * Whether an entity wants to receive digests (aggregations) of 
+	 * notifications or all notifications individually.
+	 * 
+	 * <p><b>Value: boolean</b></p>
+	 */
+	digest,
+	
+	/**
+	 * The minimum number of seconds between sending any two notifications digests
+	 * 
+	 * <p><b>Value: int</b></p>
+	 */
+	digest_frequency,
+
+	/**
+	 * The DateTime at which a leased subsscription will end ro has ended.
+	 * 
+	 * <p><b>Value: {@link Calendar}</b></p>
+	 */
+	expire,
+
+	/**
+	 * Whether an entity wants to receive an XMPP message body in addition to 
+	 * the payload format.
+	 *
+	 * <p><b>Value: boolean</b></p>
+	 */
+	include_body,
+	
+	/**
+	 * The presence states for which an entity wants to receive notifications.
+	 *
+	 * <p><b>Value: {@link PresenceState}</b></p>
+	 */
+	show_values,
+	
+	/**
+	 * 
+	 * 
+	 * <p><b>Value: </b></p>
+	 */
+	subscription_type,
+	
+	/**
+	 * 
+	 * <p><b>Value: </b></p>
+	 */
+	subscription_depth;
+	
+	public String getFieldName()
+	{
+		if (this == show_values)
+			return "pubsub#" + toString().replace('_', '-');
+		return "pubsub#" + toString();
+	}
+	
+	static public SubscribeOptionFields valueOfFromElement(String elementName)
+	{
+		String portion = elementName.substring(elementName.lastIndexOf('#' + 1));
+		
+		if ("show-values".equals(portion))
+			return show_values;
+		else
+			return valueOf(portion);
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/Subscription.java b/src/org/jivesoftware/smackx/pubsub/Subscription.java
new file mode 100644
index 0000000..19ad8a8
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/Subscription.java
@@ -0,0 +1,160 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+/**
+ * Represents a subscription to node for both requests and replies.
+ * 
+ * @author Robin Collier
+ */
+public class Subscription extends NodeExtension
+{
+	protected String jid;
+	protected String id;
+	protected State state;
+	protected boolean configRequired = false;
+	
+	public enum State
+	{
+		subscribed, unconfigured, pending, none 
+	}
+
+	/**
+	 * Used to constructs a subscription request to the root node with the specified
+	 * JID.
+	 * 
+	 * @param subscriptionJid The subscriber JID
+	 */
+	public Subscription(String subscriptionJid)
+	{
+		this(subscriptionJid, null, null, null);
+	}
+	
+	/**
+	 * Used to constructs a subscription request to the specified node with the specified
+	 * JID.
+	 * 
+	 * @param subscriptionJid The subscriber JID
+	 * @param nodeId The node id
+	 */
+	public Subscription(String subscriptionJid, String nodeId)
+	{
+		this(subscriptionJid, nodeId, null, null);
+	}
+	
+	/**
+	 * Constructs a representation of a subscription reply to the specified node 
+	 * and JID.  The server	will have supplied the subscription id and current state.
+	 * 
+	 * @param jid The JID the request was made under
+	 * @param nodeId The node subscribed to
+	 * @param subscriptionId The id of this subscription
+	 * @param state The current state of the subscription
+	 */
+	public Subscription(String jid, String nodeId, String subscriptionId, State state)
+	{
+		super(PubSubElementType.SUBSCRIPTION, nodeId);
+		this.jid = jid;
+		id = subscriptionId;
+		this.state = state;
+	}
+	
+	/**
+	 * Constructs a representation of a subscription reply to the specified node 
+	 * and JID.  The server	will have supplied the subscription id and current state
+	 * and whether the subscription need to be configured.
+	 * 
+	 * @param jid The JID the request was made under
+	 * @param nodeId The node subscribed to
+	 * @param subscriptionId The id of this subscription
+	 * @param state The current state of the subscription
+	 * @param configRequired Is configuration required to complete the subscription 
+	 */
+	public Subscription(String jid, String nodeId, String subscriptionId, State state, boolean configRequired)
+	{
+		super(PubSubElementType.SUBSCRIPTION, nodeId);
+		this.jid = jid;
+		id = subscriptionId;
+		this.state = state;
+		this.configRequired = configRequired;
+	}
+	
+	/**
+	 * Gets the JID the subscription is created for
+	 * 
+	 * @return The JID
+	 */
+	public String getJid()
+	{
+		return jid;
+	}
+	
+	/**
+	 * Gets the subscription id
+	 * 
+	 * @return The subscription id
+	 */
+	public String getId()
+	{
+		return id;
+	}
+	
+	/**
+	 * Gets the current subscription state.
+	 * 
+	 * @return Current subscription state
+	 */
+	public State getState()
+	{
+		return state;
+	}
+
+	/**
+	 * This value is only relevant when the {@link #getState()} is {@link State#unconfigured}
+	 * 
+	 * @return true if configuration is required, false otherwise
+	 */
+	public boolean isConfigRequired()
+	{
+		return configRequired;
+	}
+	
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<subscription");
+		appendAttribute(builder, "jid", jid);
+		
+		if (getNode() != null)
+			appendAttribute(builder, "node", getNode());
+		
+		if (id != null)
+			appendAttribute(builder, "subid", id);
+		
+		if (state != null)
+			appendAttribute(builder, "subscription", state.toString());
+		
+		builder.append("/>");
+		return builder.toString();
+	}
+
+	private void appendAttribute(StringBuilder builder, String att, String value)
+	{
+		builder.append(" ");
+		builder.append(att);
+		builder.append("='");
+		builder.append(value);
+		builder.append("'");
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SubscriptionEvent.java b/src/org/jivesoftware/smackx/pubsub/SubscriptionEvent.java
new file mode 100644
index 0000000..99f18d5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SubscriptionEvent.java
@@ -0,0 +1,75 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Base class to represents events that are associated to subscriptions.
+ * 
+ * @author Robin Collier
+ */
+abstract public class SubscriptionEvent extends NodeEvent
+{
+	private List<String> subIds = Collections.EMPTY_LIST;
+
+	/**
+	 * Construct an event with no subscription id's.  This can 
+	 * occur when there is only one subscription to a node.  The
+	 * event may or may not report the subscription id along 
+	 * with the event.
+	 * 
+	 * @param nodeId The id of the node the event came from
+	 */
+	protected SubscriptionEvent(String nodeId)
+	{
+		super(nodeId);
+	}
+
+	/**
+	 * Construct an event with multiple subscriptions.
+	 * 
+	 * @param nodeId The id of the node the event came from
+	 * @param subscriptionIds The list of subscription id's
+	 */
+	protected SubscriptionEvent(String nodeId, List<String> subscriptionIds)
+	{
+		super(nodeId);
+		
+		if (subscriptionIds != null)
+			subIds = subscriptionIds;
+	}
+
+	/** 
+	 * Get the subscriptions this event is associated with.
+	 * 
+	 * @return List of subscription id's
+	 */
+	public List<String> getSubscriptions()
+	{
+		return Collections.unmodifiableList(subIds);
+	}
+	
+	/**
+	 * Set the list of subscription id's for this event.
+	 * 
+	 * @param subscriptionIds The list of subscription id's
+	 */
+	protected void setSubscriptions(List<String> subscriptionIds)
+	{
+		if (subscriptionIds != null)
+			subIds = subscriptionIds;
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/SubscriptionsExtension.java b/src/org/jivesoftware/smackx/pubsub/SubscriptionsExtension.java
new file mode 100644
index 0000000..a28cbe2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/SubscriptionsExtension.java
@@ -0,0 +1,96 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Represents the element holding the list of subscription elements.
+ * 
+ * @author Robin Collier
+ */
+public class SubscriptionsExtension extends NodeExtension
+{
+	protected List<Subscription> items = Collections.EMPTY_LIST;
+	
+	/**
+	 * Subscriptions to the root node
+	 * 
+	 * @param subList The list of subscriptions
+	 */
+	public SubscriptionsExtension(List<Subscription> subList)
+	{
+		super(PubSubElementType.SUBSCRIPTIONS);
+		
+		if (subList != null)
+			items = subList;
+	}
+
+	/**
+	 * Subscriptions to the specified node.
+	 * 
+	 * @param nodeId The node subscribed to
+	 * @param subList The list of subscriptions
+	 */
+	public SubscriptionsExtension(String nodeId, List<Subscription> subList)
+	{
+		super(PubSubElementType.SUBSCRIPTIONS, nodeId);
+
+		if (subList != null)
+			items = subList;
+	}
+
+	/**
+	 * Gets the list of subscriptions.
+	 * 
+	 * @return List of subscriptions
+	 */
+	public List<Subscription> getSubscriptions()
+	{
+		return items;
+	}
+
+	@Override
+	public String toXML()
+	{
+		if ((items == null) || (items.size() == 0))
+		{
+			return super.toXML();
+		}
+		else
+		{
+			StringBuilder builder = new StringBuilder("<");
+			builder.append(getElementName());
+			
+			if (getNode() != null)
+			{
+				builder.append(" node='");
+				builder.append(getNode());
+				builder.append("'");
+			}
+			builder.append(">");
+			
+			for (Subscription item : items)
+			{
+				builder.append(item.toXML());
+			}
+			
+			builder.append("</");
+			builder.append(getElementName());
+			builder.append(">");
+			return builder.toString();
+		}
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/UnsubscribeExtension.java b/src/org/jivesoftware/smackx/pubsub/UnsubscribeExtension.java
new file mode 100644
index 0000000..ac14c60
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/UnsubscribeExtension.java
@@ -0,0 +1,73 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub;
+
+import org.jivesoftware.smackx.pubsub.util.XmlUtils;
+
+
+/**
+ * Represents an unsubscribe element.
+ * 
+ * @author Robin Collier
+ */
+public class UnsubscribeExtension extends NodeExtension
+{
+	protected String jid;
+	protected String id;
+	
+	public UnsubscribeExtension(String subscriptionJid)
+	{
+		this(subscriptionJid, null, null);
+	}
+	
+	public UnsubscribeExtension(String subscriptionJid, String nodeId)
+	{
+		this(subscriptionJid, nodeId, null);
+	}
+	
+	public UnsubscribeExtension(String jid, String nodeId, String subscriptionId)
+	{
+		super(PubSubElementType.UNSUBSCRIBE, nodeId);
+		this.jid = jid;
+		id = subscriptionId;
+	}
+	
+	public String getJid()
+	{
+		return jid;
+	}
+	
+	public String getId()
+	{
+		return id;
+	}
+	
+	@Override
+	public String toXML()
+	{
+		StringBuilder builder = new StringBuilder("<");
+		builder.append(getElementName());
+		XmlUtils.appendAttribute(builder, "jid", jid);
+		
+		if (getNode() != null)
+			XmlUtils.appendAttribute(builder, "node", getNode());
+		
+		if (id != null)
+			XmlUtils.appendAttribute(builder, "subid", id);
+		
+		builder.append("/>");
+		return builder.toString();
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/listener/ItemDeleteListener.java b/src/org/jivesoftware/smackx/pubsub/listener/ItemDeleteListener.java
new file mode 100644
index 0000000..d228e8f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/listener/ItemDeleteListener.java
@@ -0,0 +1,41 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.listener;
+
+import org.jivesoftware.smackx.pubsub.ItemDeleteEvent;
+import org.jivesoftware.smackx.pubsub.LeafNode;
+
+/**
+ * Defines the listener for item deletion events from a node.
+ * 
+ * @see LeafNode#addItemDeleteListener(ItemDeleteListener)
+ * 
+ * @author Robin Collier
+ */
+public interface ItemDeleteListener
+{
+	/**
+	 * Called when items are deleted from a node the listener is 
+	 * registered with.
+	 * 
+	 * @param items The event with item deletion details
+	 */
+	void handleDeletedItems(ItemDeleteEvent items);
+	
+	/**
+	 * Called when <b>all</b> items are deleted from a node the listener is 
+	 * registered with. 
+	 */
+	void handlePurge();
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/listener/ItemEventListener.java b/src/org/jivesoftware/smackx/pubsub/listener/ItemEventListener.java
new file mode 100644
index 0000000..714b2c0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/listener/ItemEventListener.java
@@ -0,0 +1,36 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.listener;
+
+import org.jivesoftware.smackx.pubsub.Item;
+import org.jivesoftware.smackx.pubsub.ItemPublishEvent;
+import org.jivesoftware.smackx.pubsub.LeafNode;
+
+/**
+ * Defines the listener for items being published to a node.
+ * 
+ * @see LeafNode#addItemEventListener(ItemEventListener)
+ *
+ * @author Robin Collier
+ */
+public interface ItemEventListener <T extends Item> 
+{
+	/**
+	 * Called whenever an item is published to the node the listener
+	 * is registered with.
+	 * 
+	 * @param items The publishing details.
+	 */
+	void handlePublishedItems(ItemPublishEvent<T> items);
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/listener/NodeConfigListener.java b/src/org/jivesoftware/smackx/pubsub/listener/NodeConfigListener.java
new file mode 100644
index 0000000..39db5a5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/listener/NodeConfigListener.java
@@ -0,0 +1,35 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.listener;
+
+import org.jivesoftware.smackx.pubsub.ConfigurationEvent;
+import org.jivesoftware.smackx.pubsub.LeafNode;
+
+/**
+ * Defines the listener for a node being configured.
+ * 
+ * @see LeafNode#addConfigurationListener(NodeConfigListener)
+ *
+ * @author Robin Collier
+ */
+public interface NodeConfigListener
+{
+	/**
+	 * Called whenever the node the listener
+	 * is registered with is configured.
+	 * 
+	 * @param config The configuration details.
+	 */
+	void handleNodeConfiguration(ConfigurationEvent config);
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/packet/PubSub.java b/src/org/jivesoftware/smackx/pubsub/packet/PubSub.java
new file mode 100644
index 0000000..5aa4865
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/packet/PubSub.java
@@ -0,0 +1,106 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.pubsub.PubSubElementType;
+
+/**
+ * The standard PubSub extension of an {@link IQ} packet.  This is the topmost
+ * element of all pubsub requests and replies as defined in the <a href="http://xmpp.org/extensions/xep-0060">Publish-Subscribe</a> 
+ * specification.
+ * 
+ * @author Robin Collier
+ */
+public class PubSub extends IQ
+{
+	private PubSubNamespace ns = PubSubNamespace.BASIC;
+	
+	/**
+    * Returns the XML element name of the extension sub-packet root element.
+    *
+    * @return the XML element name of the packet extension.
+    */
+    public String getElementName() {
+        return "pubsub";
+    }
+
+    /** 
+     * Returns the XML namespace of the extension sub-packet root element.
+     * According the specification the namespace is 
+     * http://jabber.org/protocol/pubsub with a specific fragment depending
+     * on the request.  The namespace is defined at <a href="http://xmpp.org/registrar/namespaces.html">XMPP Registrar</a> at
+     * 
+     * The default value has no fragment.
+     * 
+     * @return the XML namespace of the packet extension.
+     */
+    public String getNamespace() 
+    {
+        return ns.getXmlns();
+    }
+
+    /**
+     * Set the namespace for the packet if it something other than the default
+     * case of {@link PubSubNamespace#BASIC}.  The {@link #getNamespace()} method will return 
+     * the result of calling {@link PubSubNamespace#getXmlns()} on the specified enum.
+     * 
+     * @param ns - The new value for the namespace.
+     */
+	public void setPubSubNamespace(PubSubNamespace ns)
+	{
+		this.ns = ns;
+	}
+
+	public PacketExtension getExtension(PubSubElementType elem)
+	{
+		return getExtension(elem.getElementName(), elem.getNamespace().getXmlns());
+	}
+
+	/**
+	 * Returns the current value of the namespace.  The {@link #getNamespace()} method will return 
+     * the result of calling {@link PubSubNamespace#getXmlns()} this value.
+	 * 
+	 * @return The current value of the namespace.
+	 */
+	public PubSubNamespace getPubSubNamespace()
+	{
+		return ns;
+	}
+    /**
+     * Returns the XML representation of a pubsub element according the specification.
+     * 
+     * The XML representation will be inside of an iq packet like
+     * in the following example:
+     * <pre>
+     * &lt;iq type='set' id="MlIpV-4" to="pubsub.gato.home" from="gato3@gato.home/Smack"&gt;
+     *     &lt;pubsub xmlns="http://jabber.org/protocol/pubsub"&gt;
+     *                      :
+     *         Specific request extension
+     *                      :
+     *     &lt;/pubsub&gt;
+     * &lt;/iq&gt;
+     * </pre>
+     * 
+     */
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(getElementName()).append(" xmlns=\"").append(getNamespace()).append("\">");
+        buf.append(getExtensionsXML());
+        buf.append("</").append(getElementName()).append(">");
+        return buf.toString();
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/packet/PubSubNamespace.java b/src/org/jivesoftware/smackx/pubsub/packet/PubSubNamespace.java
new file mode 100644
index 0000000..eecf959
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/packet/PubSubNamespace.java
@@ -0,0 +1,63 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.packet;
+
+/**
+ * Defines all the valid namespaces that are used with the {@link PubSub} packet
+ * as defined by the specification.
+ * 
+ * @author Robin Collier
+ */
+public enum PubSubNamespace
+{
+	BASIC(null),
+	ERROR("errors"),
+	EVENT("event"),
+	OWNER("owner");
+	
+	private String fragment;
+	
+	private PubSubNamespace(String fragment)
+	{
+		this.fragment = fragment;
+	}
+	
+	public String getXmlns()
+	{
+		String ns = "http://jabber.org/protocol/pubsub";
+		
+		if (fragment != null)
+			ns += '#' + fragment;
+		
+		return ns;
+	}
+	
+	public String getFragment()
+	{
+		return fragment;
+	}
+
+	public static PubSubNamespace valueOfFromXmlns(String ns)
+	{
+		int index = ns.lastIndexOf('#');
+		
+		if (index != -1)
+		{
+			String suffix = ns.substring(ns.lastIndexOf('#')+1);
+			return valueOf(suffix.toUpperCase());
+		}
+		else
+			return BASIC;
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/packet/SyncPacketSend.java b/src/org/jivesoftware/smackx/pubsub/packet/SyncPacketSend.java
new file mode 100644
index 0000000..080129b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/packet/SyncPacketSend.java
@@ -0,0 +1,63 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.packet;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.Packet;
+
+/**
+ * Utility class for doing synchronous calls to the server.  Provides several
+ * methods for sending a packet to the server and waiting for the reply.
+ * 
+ * @author Robin Collier
+ */
+final public class SyncPacketSend
+{
+	private SyncPacketSend()
+	{	}
+	
+	static public Packet getReply(Connection connection, Packet packet, long timeout)
+		throws XMPPException
+	{
+        PacketFilter responseFilter = new PacketIDFilter(packet.getPacketID());
+        PacketCollector response = connection.createPacketCollector(responseFilter);
+        
+        connection.sendPacket(packet);
+
+        // Wait up to a certain number of seconds for a reply.
+        Packet result = response.nextResult(timeout);
+
+        // Stop queuing results
+        response.cancel();
+
+        if (result == null) {
+            throw new XMPPException("No response from server.");
+        }
+        else if (result.getError() != null) {
+            throw new XMPPException(result.getError());
+        }
+        return result;
+	}
+
+	static public Packet getReply(Connection connection, Packet packet)
+		throws XMPPException
+	{
+		return getReply(connection, packet, SmackConfiguration.getPacketReplyTimeout());
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/AffiliationProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/AffiliationProvider.java
new file mode 100644
index 0000000..892eec6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/AffiliationProvider.java
@@ -0,0 +1,37 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.Affiliation;
+
+/**
+ * Parses the affiliation element out of the reply stanza from the server
+ * as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-pubsub">affiliation schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class AffiliationProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+		return new Affiliation(attributeMap.get("jid"), attributeMap.get("node"), Affiliation.Type.valueOf(attributeMap.get("affiliation")));
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/AffiliationsProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/AffiliationsProvider.java
new file mode 100644
index 0000000..ee7af05
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/AffiliationsProvider.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.Affiliation;
+import org.jivesoftware.smackx.pubsub.AffiliationsExtension;
+
+/**
+ * Parses the affiliations element out of the reply stanza from the server
+ * as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-pubsub">affiliation schema</a>.
+ * 
+ * @author Robin Collier
+ */public class AffiliationsProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+        return new AffiliationsExtension(attributeMap.get("node"), (List<Affiliation>)content);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/ConfigEventProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/ConfigEventProvider.java
new file mode 100644
index 0000000..30e3017
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/ConfigEventProvider.java
@@ -0,0 +1,42 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.ConfigurationEvent;
+import org.jivesoftware.smackx.pubsub.ConfigureForm;
+
+/**
+ * Parses the node configuration element out of the message event stanza from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-event">configuration schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class ConfigEventProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attMap, List<? extends PacketExtension> content)
+	{
+		if (content.size() == 0)
+			return new ConfigurationEvent(attMap.get("node"));
+		else
+			return new ConfigurationEvent(attMap.get("node"), new ConfigureForm((DataForm)content.iterator().next()));
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/EventProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/EventProvider.java
new file mode 100644
index 0000000..ef5671e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/EventProvider.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.EventElement;
+import org.jivesoftware.smackx.pubsub.EventElementType;
+import org.jivesoftware.smackx.pubsub.NodeExtension;
+
+/**
+ * Parses the event element out of the message stanza from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-event">event schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class EventProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attMap, List<? extends PacketExtension> content)
+	{
+	   	return new EventElement(EventElementType.valueOf(content.get(0).getElementName()), (NodeExtension)content.get(0));
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/FormNodeProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/FormNodeProvider.java
new file mode 100644
index 0000000..da75b24
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/FormNodeProvider.java
@@ -0,0 +1,39 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.FormNode;
+import org.jivesoftware.smackx.pubsub.FormNodeType;
+
+/**
+ * Parses one of several elements used in pubsub that contain a form of some kind as a child element.  The
+ * elements and namespaces supported is defined in {@link FormNodeType}.
+ * 
+ * @author Robin Collier
+ */
+public class FormNodeProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+        return new FormNode(FormNodeType.valueOfFromElementName(currentElement, currentNamespace), attributeMap.get("node"), new Form((DataForm)content.iterator().next()));
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/ItemProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/ItemProvider.java
new file mode 100644
index 0000000..a6b8694
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/ItemProvider.java
@@ -0,0 +1,92 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smack.provider.ProviderManager;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.pubsub.Item;
+import org.jivesoftware.smackx.pubsub.PayloadItem;
+import org.jivesoftware.smackx.pubsub.SimplePayload;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses an <b>item</b> element as is defined in both the {@link PubSubNamespace#BASIC} and {@link PubSubNamespace#EVENT}
+ * namespaces.  To parse the item contents, it will use whatever {@link PacketExtensionProvider} is registered in
+ * <b>smack.providers</b> for its element name and namespace.  If no provider is registered, it will return a {@link SimplePayload}.
+ *
+ * @author Robin Collier
+ */
+public class ItemProvider implements PacketExtensionProvider {
+    public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+        String id = parser.getAttributeValue(null, "id");
+        String node = parser.getAttributeValue(null, "node");
+        String elem = parser.getName();
+
+        int tag = parser.next();
+
+        if (tag == XmlPullParser.END_TAG) {
+            return new Item(id, node);
+        } else {
+            String payloadElemName = parser.getName();
+            String payloadNS = parser.getNamespace();
+
+            if (ProviderManager.getInstance().getExtensionProvider(payloadElemName, payloadNS) == null) {
+                StringBuilder payloadText = new StringBuilder();
+                boolean done = false;
+                boolean isEmptyElement = false;
+
+                // Parse custom payload
+                while (!done) {
+                    if (tag == XmlPullParser.END_TAG && parser.getName().equals(elem)) {
+                        done = true;
+                    } else if (parser.getEventType() == XmlPullParser.START_TAG) {
+                        payloadText.append("<").append(parser.getName());
+                        if (parser.getName().equals(payloadElemName) && (!"".equals(payloadNS))) {
+                            payloadText.append(" xmlns=\"").append(payloadNS).append("\"");
+                        }
+                        int n = parser.getAttributeCount();
+                        for (int i = 0; i < n; i++) {
+                            payloadText.append(" ").append(parser.getAttributeName(i)).append("=\"")
+                                    .append(parser.getAttributeValue(i)).append("\"");
+                        }
+                        if (parser.isEmptyElementTag()) {
+                            payloadText.append("/>");
+                            isEmptyElement = true;
+                        } else {
+                            payloadText.append(">");
+                        }
+                    } else if (parser.getEventType() == XmlPullParser.END_TAG) {
+                        if (isEmptyElement) {
+                            isEmptyElement = false;
+                        } else {
+                            payloadText.append("</").append(parser.getName()).append(">");
+                        }
+                    } else if (parser.getEventType() == XmlPullParser.TEXT) {
+                        payloadText.append(parser.getText());
+                    }
+
+                    tag = parser.next();
+                }
+                return new PayloadItem<SimplePayload>(id, node, new SimplePayload(payloadElemName, payloadNS,
+                        payloadText.toString()));
+            } else {
+                return new PayloadItem<PacketExtension>(id, node, PacketParserUtils.parsePacketExtension(
+                        payloadElemName, payloadNS, parser));
+            }
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/ItemsProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/ItemsProvider.java
new file mode 100644
index 0000000..01cb9d4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/ItemsProvider.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.ItemsExtension;
+
+/**
+ * Parses the <b>items</b> element out of the message event stanza from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-event">items schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class ItemsProvider extends EmbeddedExtensionProvider
+{
+
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+        return new ItemsExtension(ItemsExtension.ItemsElementType.items, attributeMap.get("node"), content);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/PubSubProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/PubSubProvider.java
new file mode 100644
index 0000000..742f219
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/PubSubProvider.java
@@ -0,0 +1,62 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.pubsub.packet.PubSub;
+import org.jivesoftware.smackx.pubsub.packet.PubSubNamespace;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses the root pubsub packet extensions of the {@link IQ} packet and returns
+ * a {@link PubSub} instance.
+ * 
+ * @author Robin Collier
+ */
+public class PubSubProvider implements IQProvider
+{
+	public IQ parseIQ(XmlPullParser parser) throws Exception
+	{
+        PubSub pubsub = new PubSub();
+        String namespace = parser.getNamespace();
+        pubsub.setPubSubNamespace(PubSubNamespace.valueOfFromXmlns(namespace));
+        boolean done = false;
+
+        while (!done) 
+        {
+            int eventType = parser.next();
+            
+            if (eventType == XmlPullParser.START_TAG) 
+            {
+            	PacketExtension ext = PacketParserUtils.parsePacketExtension(parser.getName(), namespace, parser);
+            	
+            	if (ext != null)
+            	{
+            		pubsub.addExtension(ext);
+            	}
+            }
+            else if (eventType == XmlPullParser.END_TAG) 
+            {
+                if (parser.getName().equals("pubsub")) 
+                {
+                    done = true;
+                }
+            }
+        }
+        return pubsub;
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/RetractEventProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/RetractEventProvider.java
new file mode 100644
index 0000000..8fa3337
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/RetractEventProvider.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.RetractItem;
+
+/**
+ * Parses the <b>retract</b> element out of the message event stanza from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-event">retract schema</a>.
+ * This element is a child of the <b>items</b> element.
+ * 
+ * @author Robin Collier
+ */
+public class RetractEventProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+		return new RetractItem(attributeMap.get("id"));
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/SimpleNodeProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/SimpleNodeProvider.java
new file mode 100644
index 0000000..d2b7d30
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/SimpleNodeProvider.java
@@ -0,0 +1,37 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.NodeExtension;
+import org.jivesoftware.smackx.pubsub.PubSubElementType;
+
+/**
+ * Parses simple elements that only contain a <b>node</b> attribute.  This is common amongst many of the 
+ * elements defined in the pubsub specification.  For this common case a {@link NodeExtension} is returned. 
+ * 
+ * @author Robin Collier
+ */
+public class SimpleNodeProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+        return new NodeExtension(PubSubElementType.valueOfFromElemName(currentElement, currentNamespace), attributeMap.get("node"));
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionProvider.java
new file mode 100644
index 0000000..eccbe08
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionProvider.java
@@ -0,0 +1,52 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.jivesoftware.smackx.pubsub.Subscription;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Parses the <b>subscription</b> element out of the pubsub IQ message from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-pubsub">subscription schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class SubscriptionProvider implements PacketExtensionProvider
+{
+	public PacketExtension parseExtension(XmlPullParser parser) throws Exception
+	{
+		String jid = parser.getAttributeValue(null, "jid");
+		String nodeId = parser.getAttributeValue(null, "node");
+		String subId = parser.getAttributeValue(null, "subid");
+		String state = parser.getAttributeValue(null, "subscription");
+		boolean isRequired = false;
+
+		int tag = parser.next();
+		
+		if ((tag == XmlPullParser.START_TAG) && parser.getName().equals("subscribe-options"))
+		{
+			tag = parser.next();
+			
+			if ((tag == XmlPullParser.START_TAG) && parser.getName().equals("required"))
+				isRequired = true;
+			
+			while (parser.next() != XmlPullParser.END_TAG && parser.getName() != "subscribe-options");
+		}
+		while (parser.getEventType() != XmlPullParser.END_TAG) parser.next();
+		return new Subscription(jid, nodeId, subId, (state == null ? null : Subscription.State.valueOf(state)), isRequired);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionsProvider.java b/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionsProvider.java
new file mode 100644
index 0000000..94dc61d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/provider/SubscriptionsProvider.java
@@ -0,0 +1,38 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.provider;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smackx.provider.EmbeddedExtensionProvider;
+import org.jivesoftware.smackx.pubsub.Subscription;
+import org.jivesoftware.smackx.pubsub.SubscriptionsExtension;
+
+/**
+ * Parses the <b>subscriptions</b> element out of the pubsub IQ message from 
+ * the server as specified in the <a href="http://xmpp.org/extensions/xep-0060.html#schemas-pubsub">subscriptions schema</a>.
+ * 
+ * @author Robin Collier
+ */
+public class SubscriptionsProvider extends EmbeddedExtensionProvider
+{
+	@Override
+	protected PacketExtension createReturnExtension(String currentElement, String currentNamespace, Map<String, String> attributeMap, List<? extends PacketExtension> content)
+	{
+		return new SubscriptionsExtension(attributeMap.get("node"), (List<Subscription>)content);
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/util/NodeUtils.java b/src/org/jivesoftware/smackx/pubsub/util/NodeUtils.java
new file mode 100644
index 0000000..414601f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/util/NodeUtils.java
@@ -0,0 +1,43 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.util;
+
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.pubsub.ConfigureForm;
+import org.jivesoftware.smackx.pubsub.FormNode;
+import org.jivesoftware.smackx.pubsub.PubSubElementType;
+
+/**
+ * Utility for extracting information from packets.
+ * 
+ * @author Robin Collier
+ */
+public class NodeUtils
+{
+	/** 
+	 * Get a {@link ConfigureForm} from a packet.
+	 * 
+	 * @param packet
+	 * @param elem
+	 * @return The configuration form
+	 */
+	public static ConfigureForm getFormFromPacket(Packet packet, PubSubElementType elem)
+	{
+		FormNode config = (FormNode)packet.getExtension(elem.getElementName(), elem.getNamespace().getXmlns());
+		Form formReply = config.getForm();
+		return new ConfigureForm(formReply);
+
+	}
+}
diff --git a/src/org/jivesoftware/smackx/pubsub/util/XmlUtils.java b/src/org/jivesoftware/smackx/pubsub/util/XmlUtils.java
new file mode 100644
index 0000000..8e4a77c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/pubsub/util/XmlUtils.java
@@ -0,0 +1,35 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.pubsub.util;
+
+import java.io.StringReader;
+
+/**
+ * Simple utility for pretty printing xml.
+ * 
+ * @author Robin Collier
+ */
+public class XmlUtils
+{
+
+	static public void appendAttribute(StringBuilder builder, String att, String value)
+	{
+		builder.append(" ");
+		builder.append(att);
+		builder.append("='");
+		builder.append(value);
+		builder.append("'");
+	}
+
+}
diff --git a/src/org/jivesoftware/smackx/receipts/DeliveryReceipt.java b/src/org/jivesoftware/smackx/receipts/DeliveryReceipt.java
new file mode 100644
index 0000000..9020556
--- /dev/null
+++ b/src/org/jivesoftware/smackx/receipts/DeliveryReceipt.java
@@ -0,0 +1,77 @@
+/**
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.receipts;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.EmbeddedExtensionProvider;
+
+/**
+ * Represents a <b>message delivery receipt</b> entry as specified by
+ * <a href="http://xmpp.org/extensions/xep-0184.html">Message Delivery Receipts</a>.
+ *
+ * @author Georg Lukas
+ */
+public class DeliveryReceipt implements PacketExtension
+{
+    public static final String NAMESPACE = "urn:xmpp:receipts";
+    public static final String ELEMENT = "received";
+
+    private String id; /// original ID of the delivered message
+
+    public DeliveryReceipt(String id)
+    {
+        this.id = id;
+    }
+
+    public String getId()
+    {
+        return id;
+    }
+
+    @Override
+    public String getElementName()
+    {
+        return ELEMENT;
+    }
+
+    @Override
+    public String getNamespace()
+    {
+        return NAMESPACE;
+    }
+
+    @Override
+    public String toXML()
+    {
+        return "<received xmlns='" + NAMESPACE + "' id='" + id + "'/>";
+    }
+
+    /**
+     * This Provider parses and returns DeliveryReceipt packets.
+     */
+    public static class Provider extends EmbeddedExtensionProvider
+    {
+
+        @Override
+        protected PacketExtension createReturnExtension(String currentElement, String currentNamespace,
+                Map<String, String> attributeMap, List<? extends PacketExtension> content)
+        {
+            return new DeliveryReceipt(attributeMap.get("id"));
+        }
+
+    }
+}
diff --git a/src/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java b/src/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java
new file mode 100644
index 0000000..125b87e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/receipts/DeliveryReceiptManager.java
@@ -0,0 +1,202 @@
+/**
+ * Copyright 2013 Georg Lukas
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.receipts;
+
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+import java.util.WeakHashMap;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.ConnectionCreationListener;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketExtensionFilter;
+import org.jivesoftware.smack.packet.Message;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+
+/**
+ * Manager for XEP-0184: Message Delivery Receipts. This class implements
+ * the manager for {@link DeliveryReceipt} support, enabling and disabling of
+ * automatic DeliveryReceipt transmission.
+ *
+ * @author Georg Lukas
+ */
+public class DeliveryReceiptManager implements PacketListener {
+
+    private static Map<Connection, DeliveryReceiptManager> instances =
+            Collections.synchronizedMap(new WeakHashMap<Connection, DeliveryReceiptManager>());
+
+    static {
+        Connection.addConnectionCreationListener(new ConnectionCreationListener() {
+            public void connectionCreated(Connection connection) {
+                new DeliveryReceiptManager(connection);
+            }
+        });
+    }
+
+    private Connection connection;
+    private boolean auto_receipts_enabled = false;
+    private Set<ReceiptReceivedListener> receiptReceivedListeners = Collections
+            .synchronizedSet(new HashSet<ReceiptReceivedListener>());
+
+    private DeliveryReceiptManager(Connection connection) {
+        ServiceDiscoveryManager sdm = ServiceDiscoveryManager.getInstanceFor(connection);
+        sdm.addFeature(DeliveryReceipt.NAMESPACE);
+        this.connection = connection;
+        instances.put(connection, this);
+
+        // register listener for delivery receipts and requests
+        connection.addPacketListener(this, new PacketExtensionFilter(DeliveryReceipt.NAMESPACE));
+    }
+
+    /**
+     * Obtain the DeliveryReceiptManager responsible for a connection.
+     *
+     * @param connection the connection object.
+     *
+     * @return the DeliveryReceiptManager instance for the given connection
+     */
+    synchronized public static DeliveryReceiptManager getInstanceFor(Connection connection) {
+        DeliveryReceiptManager receiptManager = instances.get(connection);
+
+        if (receiptManager == null) {
+            receiptManager = new DeliveryReceiptManager(connection);
+        }
+
+        return receiptManager;
+    }
+
+    /**
+     * Returns true if Delivery Receipts are supported by a given JID
+     * 
+     * @param jid
+     * @return true if supported
+     */
+    public boolean isSupported(String jid) {
+        try {
+            DiscoverInfo result =
+                ServiceDiscoveryManager.getInstanceFor(connection).discoverInfo(jid);
+            return result.containsFeature(DeliveryReceipt.NAMESPACE);
+        }
+        catch (XMPPException e) {
+            return false;
+        }
+    }
+
+    // handle incoming receipts and receipt requests
+    @Override
+    public void processPacket(Packet packet) {
+        DeliveryReceipt dr = (DeliveryReceipt)packet.getExtension(
+                DeliveryReceipt.ELEMENT, DeliveryReceipt.NAMESPACE);
+        if (dr != null) {
+            // notify listeners of incoming receipt
+            for (ReceiptReceivedListener l : receiptReceivedListeners) {
+                l.onReceiptReceived(packet.getFrom(), packet.getTo(), dr.getId());
+            }
+
+        }
+
+        // if enabled, automatically send a receipt
+        if (auto_receipts_enabled) {
+            DeliveryReceiptRequest drr = (DeliveryReceiptRequest)packet.getExtension(
+                    DeliveryReceiptRequest.ELEMENT, DeliveryReceipt.NAMESPACE);
+            if (drr != null) {
+                Message ack = new Message(packet.getFrom(), Message.Type.normal);
+                ack.addExtension(new DeliveryReceipt(packet.getPacketID()));
+                connection.sendPacket(ack);
+            }
+        }
+    }
+
+    /**
+     * Configure whether the {@link DeliveryReceiptManager} should automatically
+     * reply to incoming {@link DeliveryReceipt}s. By default, this feature is off.
+     *
+     * @param new_state whether automatic transmission of
+     *                  DeliveryReceipts should be enabled or disabled
+     */
+    public void setAutoReceiptsEnabled(boolean new_state) {
+        auto_receipts_enabled = new_state;
+    }
+
+    /**
+     * Helper method to enable automatic DeliveryReceipt transmission.
+     */
+    public void enableAutoReceipts() {
+        setAutoReceiptsEnabled(true);
+    }
+
+    /**
+     * Helper method to disable automatic DeliveryReceipt transmission.
+     */
+    public void disableAutoReceipts() {
+        setAutoReceiptsEnabled(false);
+    }
+
+    /**
+     * Check if AutoReceipts are enabled on this connection.
+     */
+    public boolean getAutoReceiptsEnabled() {
+        return this.auto_receipts_enabled;
+    }
+
+    /**
+     * Get informed about incoming delivery receipts with a {@link ReceiptReceivedListener}.
+     * 
+     * @param listener the listener to be informed about new receipts
+     */
+    public void addReceiptReceivedListener(ReceiptReceivedListener listener) {
+        receiptReceivedListeners.add(listener);
+    }
+
+    /**
+     * Stop getting informed about incoming delivery receipts.
+     * 
+     * @param listener the listener to be removed
+     */
+    public void removeReceiptReceivedListener(ReceiptReceivedListener listener) {
+        receiptReceivedListeners.remove(listener);
+    }
+
+    /**
+     * Test if a packet requires a delivery receipt.
+     *
+     * @param p Packet object to check for a DeliveryReceiptRequest
+     *
+     * @return true if a delivery receipt was requested
+     */
+    public static boolean hasDeliveryReceiptRequest(Packet p) {
+        return (p.getExtension(DeliveryReceiptRequest.ELEMENT,
+                    DeliveryReceipt.NAMESPACE) != null);
+    }
+
+    /**
+     * Add a delivery receipt request to an outgoing packet.
+     *
+     * Only message packets may contain receipt requests as of XEP-0184,
+     * therefore only allow Message as the parameter type.
+     *
+     * @param m Message object to add a request to
+     */
+    public static void addDeliveryReceiptRequest(Message m) {
+        m.addExtension(new DeliveryReceiptRequest());
+    }
+}
diff --git a/src/org/jivesoftware/smackx/receipts/DeliveryReceiptRequest.java b/src/org/jivesoftware/smackx/receipts/DeliveryReceiptRequest.java
new file mode 100644
index 0000000..1b5ed3b
--- /dev/null
+++ b/src/org/jivesoftware/smackx/receipts/DeliveryReceiptRequest.java
@@ -0,0 +1,54 @@
+/*
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.receipts;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Represents a <b>message delivery receipt request</b> entry as specified by
+ * <a href="http://xmpp.org/extensions/xep-0184.html">Message Delivery Receipts</a>.
+ *
+ * @author Georg Lukas
+ */
+public class DeliveryReceiptRequest implements PacketExtension
+{
+    public static final String ELEMENT = "request";
+
+    public String getElementName()
+    {
+        return ELEMENT;
+    }
+
+    public String getNamespace()
+    {
+        return DeliveryReceipt.NAMESPACE;
+    }
+
+    public String toXML()
+    {
+        return "<request xmlns='" + DeliveryReceipt.NAMESPACE + "'/>";
+    }
+
+    /**
+     * This Provider parses and returns DeliveryReceiptRequest packets.
+     */
+    public static class Provider implements PacketExtensionProvider {
+        @Override
+        public PacketExtension parseExtension(XmlPullParser parser) {
+            return new DeliveryReceiptRequest();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/receipts/ReceiptReceivedListener.java b/src/org/jivesoftware/smackx/receipts/ReceiptReceivedListener.java
new file mode 100644
index 0000000..3183113
--- /dev/null
+++ b/src/org/jivesoftware/smackx/receipts/ReceiptReceivedListener.java
@@ -0,0 +1,26 @@
+/**
+ * Copyright 2013 Georg Lukas
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.receipts;
+
+/**
+ * Interface for received receipt notifications.
+ * 
+ * Implement this and add a listener to get notified. 
+ */
+public interface ReceiptReceivedListener {
+    void onReceiptReceived(String fromJid, String toJid, String receiptId);
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/search/SimpleUserSearch.java b/src/org/jivesoftware/smackx/search/SimpleUserSearch.java
new file mode 100644
index 0000000..74a70f0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/search/SimpleUserSearch.java
@@ -0,0 +1,151 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.search;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.ReportedData;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * SimpleUserSearch is used to support the non-dataform type of JEP 55. This provides
+ * the mechanism for allowing always type ReportedData to be returned by any search result,
+ * regardless of the form of the data returned from the server.
+ *
+ * @author Derek DeMoro
+ */
+class SimpleUserSearch extends IQ {
+
+    private Form form;
+    private ReportedData data;
+
+    public void setForm(Form form) {
+        this.form = form;
+    }
+
+    public ReportedData getReportedData() {
+        return data;
+    }
+
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:search\">");
+        buf.append(getItemsToSearch());
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    private String getItemsToSearch() {
+        StringBuilder buf = new StringBuilder();
+
+        if (form == null) {
+            form = Form.getFormFrom(this);
+        }
+
+        if (form == null) {
+            return "";
+        }
+
+        Iterator<FormField> fields = form.getFields();
+        while (fields.hasNext()) {
+            FormField field = fields.next();
+            String name = field.getVariable();
+            String value = getSingleValue(field);
+            if (value.trim().length() > 0) {
+                buf.append("<").append(name).append(">").append(value).append("</").append(name).append(">");
+            }
+        }
+
+        return buf.toString();
+    }
+
+    private static String getSingleValue(FormField formField) {
+        Iterator<String> values = formField.getValues();
+        while (values.hasNext()) {
+            return values.next();
+        }
+        return "";
+    }
+
+    protected void parseItems(XmlPullParser parser) throws Exception {
+        ReportedData data = new ReportedData();
+        data.addColumn(new ReportedData.Column("JID", "jid", "text-single"));
+
+        boolean done = false;
+
+        List<ReportedData.Field> fields = new ArrayList<ReportedData.Field>();
+        while (!done) {
+            if (parser.getAttributeCount() > 0) {
+                String jid = parser.getAttributeValue("", "jid");
+                List<String> valueList = new ArrayList<String>();
+                valueList.add(jid);
+                ReportedData.Field field = new ReportedData.Field("jid", valueList);
+                fields.add(field);
+            }
+
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG && parser.getName().equals("item")) {
+                fields = new ArrayList<ReportedData.Field>();
+            }
+            else if (eventType == XmlPullParser.END_TAG && parser.getName().equals("item")) {
+                ReportedData.Row row = new ReportedData.Row(fields);
+                data.addRow(row);
+            }
+            else if (eventType == XmlPullParser.START_TAG) {
+                String name = parser.getName();
+                String value = parser.nextText();
+
+                List<String> valueList = new ArrayList<String>();
+                valueList.add(value);
+                ReportedData.Field field = new ReportedData.Field(name, valueList);
+                fields.add(field);
+
+                boolean exists = false;
+                Iterator<ReportedData.Column> cols = data.getColumns();
+                while (cols.hasNext()) {
+                    ReportedData.Column column = cols.next();
+                    if (column.getVariable().equals(name)) {
+                        exists = true;
+                    }
+                }
+
+                // Column name should be the same
+                if (!exists) {
+                    ReportedData.Column column = new ReportedData.Column(name, name, "text-single");
+                    data.addColumn(column);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+
+        }
+
+        this.data = data;
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smackx/search/UserSearch.java b/src/org/jivesoftware/smackx/search/UserSearch.java
new file mode 100644
index 0000000..781dd9a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/search/UserSearch.java
@@ -0,0 +1,255 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.search;
+
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.ReportedData;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Implements the protocol currently used to search information repositories on the Jabber network. To date, the jabber:iq:search protocol
+ * has been used mainly to search for people who have registered with user directories (e.g., the "Jabber User Directory" hosted at users.jabber.org).
+ * However, the jabber:iq:search protocol is not limited to user directories, and could be used to search other Jabber information repositories
+ * (such as chatroom directories) or even to provide a Jabber interface to conventional search engines.
+ * <p/>
+ * The basic functionality is to query an information repository regarding the possible search fields, to send a search query, and to receive search results.
+ *
+ * @author Derek DeMoro
+ */
+public class UserSearch extends IQ {
+
+    /**
+     * Creates a new instance of UserSearch.
+     */
+    public UserSearch() {
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<query xmlns=\"jabber:iq:search\">");
+        buf.append(getExtensionsXML());
+        buf.append("</query>");
+        return buf.toString();
+    }
+
+    /**
+     * Returns the form for all search fields supported by the search service.
+     *
+     * @param con           the current Connection.
+     * @param searchService the search service to use. (ex. search.jivesoftware.com)
+     * @return the search form received by the server.
+     * @throws org.jivesoftware.smack.XMPPException
+     *          thrown if a server error has occurred.
+     */
+    public Form getSearchForm(Connection con, String searchService) throws XMPPException {
+        UserSearch search = new UserSearch();
+        search.setType(IQ.Type.GET);
+        search.setTo(searchService);
+
+        PacketCollector collector = con.createPacketCollector(new PacketIDFilter(search.getPacketID()));
+        con.sendPacket(search);
+
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return Form.getFormFrom(response);
+    }
+
+    /**
+     * Sends the filled out answer form to be sent and queried by the search service.
+     *
+     * @param con           the current Connection.
+     * @param searchForm    the <code>Form</code> to send for querying.
+     * @param searchService the search service to use. (ex. search.jivesoftware.com)
+     * @return ReportedData the data found from the query.
+     * @throws org.jivesoftware.smack.XMPPException
+     *          thrown if a server error has occurred.
+     */
+    public ReportedData sendSearchForm(Connection con, Form searchForm, String searchService) throws XMPPException {
+        UserSearch search = new UserSearch();
+        search.setType(IQ.Type.SET);
+        search.setTo(searchService);
+        search.addExtension(searchForm.getDataFormToSend());
+
+        PacketCollector collector = con.createPacketCollector(new PacketIDFilter(search.getPacketID()));
+
+        con.sendPacket(search);
+
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            return sendSimpleSearchForm(con, searchForm, searchService);
+        }
+
+
+        return ReportedData.getReportedDataFrom(response);
+    }
+
+    /**
+     * Sends the filled out answer form to be sent and queried by the search service.
+     *
+     * @param con           the current Connection.
+     * @param searchForm    the <code>Form</code> to send for querying.
+     * @param searchService the search service to use. (ex. search.jivesoftware.com)
+     * @return ReportedData the data found from the query.
+     * @throws org.jivesoftware.smack.XMPPException
+     *          thrown if a server error has occurred.
+     */
+    public ReportedData sendSimpleSearchForm(Connection con, Form searchForm, String searchService) throws XMPPException {
+        SimpleUserSearch search = new SimpleUserSearch();
+        search.setForm(searchForm);
+        search.setType(IQ.Type.SET);
+        search.setTo(searchService);
+
+        PacketCollector collector = con.createPacketCollector(new PacketIDFilter(search.getPacketID()));
+
+        con.sendPacket(search);
+
+        IQ response = (IQ) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+
+        if (response instanceof SimpleUserSearch) {
+            return ((SimpleUserSearch) response).getReportedData();
+        }
+        return null;
+    }
+
+    /**
+     * Internal Search service Provider.
+     */
+    public static class Provider implements IQProvider {
+
+        /**
+         * Provider Constructor.
+         */
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            UserSearch search = null;
+            SimpleUserSearch simpleUserSearch = new SimpleUserSearch();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG && parser.getName().equals("instructions")) {
+                    buildDataForm(simpleUserSearch, parser.nextText(), parser);
+                    return simpleUserSearch;
+                }
+                else if (eventType == XmlPullParser.START_TAG && parser.getName().equals("item")) {
+                    simpleUserSearch.parseItems(parser);
+                    return simpleUserSearch;
+                }
+                else if (eventType == XmlPullParser.START_TAG && parser.getNamespace().equals("jabber:x:data")) {
+                    // Otherwise, it must be a packet extension.
+                    search = new UserSearch();
+                    search.addExtension(PacketParserUtils.parsePacketExtension(parser.getName(),
+                            parser.getNamespace(), parser));
+
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("query")) {
+                        done = true;
+                    }
+                }
+            }
+
+            if (search != null) {
+                return search;
+            }
+            return simpleUserSearch;
+        }
+    }
+
+    private static void buildDataForm(SimpleUserSearch search, String instructions, XmlPullParser parser) throws Exception {
+        DataForm dataForm = new DataForm(Form.TYPE_FORM);
+        boolean done = false;
+        dataForm.setTitle("User Search");
+        dataForm.addInstruction(instructions);
+        while (!done) {
+            int eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG && !parser.getNamespace().equals("jabber:x:data")) {
+                String name = parser.getName();
+                FormField field = new FormField(name);
+
+                // Handle hard coded values.
+                if(name.equals("first")){
+                    field.setLabel("First Name");
+                }
+                else if(name.equals("last")){
+                    field.setLabel("Last Name");
+                }
+                else if(name.equals("email")){
+                    field.setLabel("Email Address");
+                }
+                else if(name.equals("nick")){
+                    field.setLabel("Nickname");
+                }
+
+                field.setType(FormField.TYPE_TEXT_SINGLE);
+                dataForm.addField(field);
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("query")) {
+                    done = true;
+                }
+            }
+            else if (eventType == XmlPullParser.START_TAG && parser.getNamespace().equals("jabber:x:data")) {
+                search.addExtension(PacketParserUtils.parsePacketExtension(parser.getName(),
+                        parser.getNamespace(), parser));
+                done = true;
+            }
+        }
+        if (search.getExtension("x", "jabber:x:data") == null) {
+            search.addExtension(dataForm);
+        }
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smackx/search/UserSearchManager.java b/src/org/jivesoftware/smackx/search/UserSearchManager.java
new file mode 100644
index 0000000..858c2a7
--- /dev/null
+++ b/src/org/jivesoftware/smackx/search/UserSearchManager.java
@@ -0,0 +1,124 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.search;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.ReportedData;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.DiscoverItems;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * The UserSearchManager is a facade built upon Jabber Search Services (JEP-055) to allow for searching
+ * repositories on a Jabber Server. This implementation allows for transparency of implementation of
+ * searching (DataForms or No DataForms), but allows the user to simply use the DataForm model for both
+ * types of support.
+ * <pre>
+ * Connection con = new XMPPConnection("jabber.org");
+ * con.login("john", "doe");
+ * UserSearchManager search = new UserSearchManager(con, "users.jabber.org");
+ * Form searchForm = search.getSearchForm();
+ * Form answerForm = searchForm.createAnswerForm();
+ * answerForm.setAnswer("last", "DeMoro");
+ * ReportedData data = search.getSearchResults(answerForm);
+ * // Use Returned Data
+ * </pre>
+ *
+ * @author Derek DeMoro
+ */
+public class UserSearchManager {
+
+    private Connection con;
+    private UserSearch userSearch;
+
+    /**
+     * Creates a new UserSearchManager.
+     *
+     * @param con the Connection to use.
+     */
+    public UserSearchManager(Connection con) {
+        this.con = con;
+        userSearch = new UserSearch();
+    }
+
+    /**
+     * Returns the form to fill out to perform a search.
+     *
+     * @param searchService the search service to query.
+     * @return the form to fill out to perform a search.
+     * @throws XMPPException thrown if a server error has occurred.
+     */
+    public Form getSearchForm(String searchService) throws XMPPException {
+        return userSearch.getSearchForm(con, searchService);
+    }
+
+    /**
+     * Submits a search form to the server and returns the resulting information
+     * in the form of <code>ReportedData</code>
+     *
+     * @param searchForm    the <code>Form</code> to submit for searching.
+     * @param searchService the name of the search service to use.
+     * @return the ReportedData returned by the server.
+     * @throws XMPPException thrown if a server error has occurred.
+     */
+    public ReportedData getSearchResults(Form searchForm, String searchService) throws XMPPException {
+        return userSearch.sendSearchForm(con, searchForm, searchService);
+    }
+
+
+    /**
+     * Returns a collection of search services found on the server.
+     *
+     * @return a Collection of search services found on the server.
+     * @throws XMPPException thrown if a server error has occurred.
+     */
+    public Collection<String> getSearchServices() throws XMPPException {
+        final List<String> searchServices = new ArrayList<String>();
+        ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(con);
+        DiscoverItems items = discoManager.discoverItems(con.getServiceName());
+        Iterator<DiscoverItems.Item> iter = items.getItems();
+        while (iter.hasNext()) {
+            DiscoverItems.Item item = iter.next();
+            try {
+                DiscoverInfo info;
+                try {
+                    info = discoManager.discoverInfo(item.getEntityID());
+                }
+                catch (XMPPException e) {
+                    // Ignore Case
+                    continue;
+                }
+
+                if (info.containsFeature("jabber:iq:search")) {
+                    searchServices.add(item.getEntityID());
+                }
+            }
+            catch (Exception e) {
+                // No info found.
+                break;
+            }
+        }
+        return searchServices;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/MetaData.java b/src/org/jivesoftware/smackx/workgroup/MetaData.java
new file mode 100644
index 0000000..115a79c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/MetaData.java
@@ -0,0 +1,68 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smackx.workgroup.util.MetaDataUtils;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+
+/**
+ * MetaData packet extension.
+ */
+public class MetaData implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "metadata";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    private Map<String, List<String>> metaData;
+
+    public MetaData(Map<String, List<String>> metaData) {
+        this.metaData = metaData;
+    }
+
+    /**
+     * @return the Map of metadata contained by this instance
+     */
+    public Map<String, List<String>> getMetaData() {
+        return metaData;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        return MetaDataUtils.serializeMetaData(this.getMetaData());
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/QueueUser.java b/src/org/jivesoftware/smackx/workgroup/QueueUser.java
new file mode 100644
index 0000000..89a1899
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/QueueUser.java
@@ -0,0 +1,85 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup;
+
+import java.util.Date;
+
+/**
+ * An immutable class which wraps up customer-in-queue data return from the server; depending on
+ * the type of information dispatched from the server, not all information will be available in
+ * any given instance.
+ *
+ * @author loki der quaeler
+ */
+public class QueueUser {
+
+    private String userID;
+
+    private int queuePosition;
+    private int estimatedTime;
+    private Date joinDate;
+
+    /**
+     * @param uid the user jid of the customer in the queue
+     * @param position the position customer sits in the queue
+     * @param time the estimate of how much longer the customer will be in the queue in seconds
+     * @param joinedAt the timestamp of when the customer entered the queue
+     */
+    public QueueUser (String uid, int position, int time, Date joinedAt) {
+        super();
+
+        this.userID = uid;
+        this.queuePosition = position;
+        this.estimatedTime = time;
+        this.joinDate = joinedAt;
+    }
+
+    /**
+     * @return the user jid of the customer in the queue
+     */
+    public String getUserID () {
+        return this.userID;
+    }
+
+    /**
+     * @return the position in the queue at which the customer sits, or -1 if the update which
+     *          this instance embodies is only a time update instead
+     */
+    public int getQueuePosition () {
+        return this.queuePosition;
+    }
+
+    /**
+     * @return the estimated time remaining of the customer in the queue in seconds, or -1 if
+     *          if the update which this instance embodies is only a position update instead
+     */
+    public int getEstimatedRemainingTime () {
+        return this.estimatedTime;
+    }
+
+    /**
+     * @return the timestamp of when this customer entered the queue, or null if the server did not
+     *          provide this information
+     */
+    public Date getQueueJoinTimestamp () {
+        return this.joinDate;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitation.java b/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitation.java
new file mode 100644
index 0000000..ac3b5b6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitation.java
@@ -0,0 +1,134 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * An immutable class wrapping up the basic information which comprises a group chat invitation.
+ *
+ * @author loki der quaeler
+ */
+public class WorkgroupInvitation {
+
+    protected String uniqueID;
+
+    protected String sessionID;
+
+    protected String groupChatName;
+    protected String issuingWorkgroupName;
+    protected String messageBody;
+    protected String invitationSender;
+    protected Map<String, List<String>> metaData;
+
+    /**
+     * This calls the 5-argument constructor with a null MetaData argument value
+     *
+     * @param jid the jid string with which the issuing AgentSession or Workgroup instance
+     *                  was created
+     * @param group the jid of the room to which the person is invited
+     * @param workgroup the jid of the workgroup issuing the invitation
+     * @param sessID the session id associated with the pending chat
+     * @param msgBody the body of the message which contained the invitation
+     * @param from the user jid who issued the invitation, if known, null otherwise
+     */
+    public WorkgroupInvitation (String jid, String group, String workgroup,
+                       String sessID, String msgBody, String from) {
+        this(jid, group, workgroup, sessID, msgBody, from, null);
+    }
+
+    /**
+     * @param jid the jid string with which the issuing AgentSession or Workgroup instance
+     *                  was created
+     * @param group the jid of the room to which the person is invited
+     * @param workgroup the jid of the workgroup issuing the invitation
+     * @param sessID the session id associated with the pending chat
+     * @param msgBody the body of the message which contained the invitation
+     * @param from the user jid who issued the invitation, if known, null otherwise
+     * @param metaData the metadata sent with the invitation
+     */
+    public WorkgroupInvitation (String jid, String group, String workgroup, String sessID, String msgBody,
+                       String from, Map<String, List<String>> metaData) {
+        super();
+
+        this.uniqueID = jid;
+        this.sessionID = sessID;
+        this.groupChatName = group;
+        this.issuingWorkgroupName = workgroup;
+        this.messageBody = msgBody;
+        this.invitationSender = from;
+        this.metaData = metaData;
+    }
+
+    /**
+     * @return the jid string with which the issuing AgentSession or Workgroup instance
+     *  was created.
+     */
+    public String getUniqueID () {
+        return this.uniqueID;
+    }
+
+    /**
+     * @return the session id associated with the pending chat; working backwards temporally,
+     *              this session id should match the session id to the corresponding offer request
+     *              which resulted in this invitation.
+     */
+    public String getSessionID () {
+        return this.sessionID;
+    }
+
+    /**
+     * @return the jid of the room to which the person is invited.
+     */
+    public String getGroupChatName () {
+        return this.groupChatName;
+    }
+
+    /**
+     * @return the name of the workgroup from which the invitation was issued.
+     */
+    public String getWorkgroupName () {
+        return this.issuingWorkgroupName;
+    }
+
+    /**
+     * @return the contents of the body-block of the message that housed this invitation.
+     */
+    public String getMessageBody () {
+        return this.messageBody;
+    }
+
+    /**
+     * @return the user who issued the invitation, or null if it wasn't known.
+     */
+    public String getInvitationSender () {
+        return this.invitationSender;
+    }
+
+    /**
+     * @return the meta data associated with the invitation, or null if this instance was
+     *              constructed with none
+     */
+    public Map<String, List<String>> getMetaData () {
+        return this.metaData;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitationListener.java b/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitationListener.java
new file mode 100644
index 0000000..bc73242
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/WorkgroupInvitationListener.java
@@ -0,0 +1,39 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup;
+
+/**
+ * An interface which all classes interested in hearing about group chat invitations should
+ *  implement.
+ *
+ * @author loki der quaeler
+ */
+public interface WorkgroupInvitationListener {
+
+    /**
+     * The implementing class instance will be notified via this method when an invitation
+     *  to join a group chat has been received from the server.
+     *
+     * @param invitation an Invitation instance embodying the information pertaining to the
+     *                      invitation
+     */
+    public void invitationReceived(WorkgroupInvitation invitation);
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/Agent.java b/src/org/jivesoftware/smackx/workgroup/agent/Agent.java
new file mode 100644
index 0000000..bebac37
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/Agent.java
@@ -0,0 +1,138 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smackx.workgroup.packet.AgentInfo;
+import org.jivesoftware.smackx.workgroup.packet.AgentWorkgroups;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+
+import java.util.Collection;
+
+/**
+ * The <code>Agent</code> class is used to represent one agent in a Workgroup Queue.
+ *
+ * @author Derek DeMoro
+ */
+public class Agent {
+    private Connection connection;
+    private String workgroupJID;
+
+    public static Collection<String> getWorkgroups(String serviceJID, String agentJID, Connection connection) throws XMPPException {
+        AgentWorkgroups request = new AgentWorkgroups(agentJID);
+        request.setTo(serviceJID);
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        // Send the request
+        connection.sendPacket(request);
+
+        AgentWorkgroups response = (AgentWorkgroups)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response.getWorkgroups();
+    }
+
+    /**
+     * Constructs an Agent.
+     */
+    Agent(Connection connection, String workgroupJID) {
+        this.connection = connection;
+        this.workgroupJID = workgroupJID;
+    }
+
+    /**
+     * Return the agents JID
+     *
+     * @return - the agents JID.
+     */
+    public String getUser() {
+        return connection.getUser();
+    }
+
+    /**
+     * Return the agents name.
+     *
+     * @return - the agents name.
+     */
+    public String getName() throws XMPPException {
+        AgentInfo agentInfo = new AgentInfo();
+        agentInfo.setType(IQ.Type.GET);
+        agentInfo.setTo(workgroupJID);
+        agentInfo.setFrom(getUser());
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(agentInfo.getPacketID()));
+        // Send the request
+        connection.sendPacket(agentInfo);
+
+        AgentInfo response = (AgentInfo)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response.getName();
+    }
+
+    /**
+     * Changes the name of the agent in the server. The server may have this functionality
+     * disabled for all the agents or for this agent in particular. If the agent is not
+     * allowed to change his name then an exception will be thrown with a service_unavailable
+     * error code.
+     *
+     * @param newName the new name of the agent.
+     * @throws XMPPException if the agent is not allowed to change his name or no response was
+     *                       obtained from the server.
+     */
+    public void setName(String newName) throws XMPPException {
+        AgentInfo agentInfo = new AgentInfo();
+        agentInfo.setType(IQ.Type.SET);
+        agentInfo.setTo(workgroupJID);
+        agentInfo.setFrom(getUser());
+        agentInfo.setName(newName);
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(agentInfo.getPacketID()));
+        // Send the request
+        connection.sendPacket(agentInfo);
+
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/AgentRoster.java b/src/org/jivesoftware/smackx/workgroup/agent/AgentRoster.java
new file mode 100644
index 0000000..70c95ee
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/AgentRoster.java
@@ -0,0 +1,386 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smackx.workgroup.packet.AgentStatus;
+import org.jivesoftware.smackx.workgroup.packet.AgentStatusRequest;
+import org.jivesoftware.smack.PacketListener;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.filter.PacketFilter;
+import org.jivesoftware.smack.filter.PacketTypeFilter;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.packet.Presence;
+import org.jivesoftware.smack.util.StringUtils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Manges information about the agents in a workgroup and their presence.
+ *
+ * @author Matt Tucker
+ * @see AgentSession#getAgentRoster()
+ */
+public class AgentRoster {
+
+    private static final int EVENT_AGENT_ADDED = 0;
+    private static final int EVENT_AGENT_REMOVED = 1;
+    private static final int EVENT_PRESENCE_CHANGED = 2;
+
+    private Connection connection;
+    private String workgroupJID;
+    private List<String> entries;
+    private List<AgentRosterListener> listeners;
+    private Map<String, Map<String, Presence>> presenceMap;
+    // The roster is marked as initialized when at least a single roster packet
+    // has been recieved and processed.
+    boolean rosterInitialized = false;
+
+    /**
+     * Constructs a new AgentRoster.
+     *
+     * @param connection an XMPP connection.
+     */
+    AgentRoster(Connection connection, String workgroupJID) {
+        this.connection = connection;
+        this.workgroupJID = workgroupJID;
+        entries = new ArrayList<String>();
+        listeners = new ArrayList<AgentRosterListener>();
+        presenceMap = new HashMap<String, Map<String, Presence>>();
+        // Listen for any roster packets.
+        PacketFilter rosterFilter = new PacketTypeFilter(AgentStatusRequest.class);
+        connection.addPacketListener(new AgentStatusListener(), rosterFilter);
+        // Listen for any presence packets.
+        connection.addPacketListener(new PresencePacketListener(),
+                new PacketTypeFilter(Presence.class));
+
+        // Send request for roster.
+        AgentStatusRequest request = new AgentStatusRequest();
+        request.setTo(workgroupJID);
+        connection.sendPacket(request);
+    }
+
+    /**
+     * Reloads the entire roster from the server. This is an asynchronous operation,
+     * which means the method will return immediately, and the roster will be
+     * reloaded at a later point when the server responds to the reload request.
+     */
+    public void reload() {
+        AgentStatusRequest request = new AgentStatusRequest();
+        request.setTo(workgroupJID);
+        connection.sendPacket(request);
+    }
+
+    /**
+     * Adds a listener to this roster. The listener will be fired anytime one or more
+     * changes to the roster are pushed from the server.
+     *
+     * @param listener an agent roster listener.
+     */
+    public void addListener(AgentRosterListener listener) {
+        synchronized (listeners) {
+            if (!listeners.contains(listener)) {
+                listeners.add(listener);
+
+                // Fire events for the existing entries and presences in the roster
+                for (Iterator<String> it = getAgents().iterator(); it.hasNext();) {
+                    String jid = it.next();
+                    // Check again in case the agent is no longer in the roster (highly unlikely
+                    // but possible)
+                    if (entries.contains(jid)) {
+                        // Fire the agent added event
+                        listener.agentAdded(jid);
+                        Map<String,Presence> userPresences = presenceMap.get(jid);
+                        if (userPresences != null) {
+                            Iterator<Presence> presences = userPresences.values().iterator();
+                            while (presences.hasNext()) {
+                                // Fire the presence changed event
+                                listener.presenceChanged(presences.next());
+                            }
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    /**
+     * Removes a listener from this roster. The listener will be fired anytime one or more
+     * changes to the roster are pushed from the server.
+     *
+     * @param listener a roster listener.
+     */
+    public void removeListener(AgentRosterListener listener) {
+        synchronized (listeners) {
+            listeners.remove(listener);
+        }
+    }
+
+    /**
+     * Returns a count of all agents in the workgroup.
+     *
+     * @return the number of agents in the workgroup.
+     */
+    public int getAgentCount() {
+        return entries.size();
+    }
+
+    /**
+     * Returns all agents (String JID values) in the workgroup.
+     *
+     * @return all entries in the roster.
+     */
+    public Set<String> getAgents() {
+        Set<String> agents = new HashSet<String>();
+        synchronized (entries) {
+            for (Iterator<String> i = entries.iterator(); i.hasNext();) {
+                agents.add(i.next());
+            }
+        }
+        return Collections.unmodifiableSet(agents);
+    }
+
+    /**
+     * Returns true if the specified XMPP address is an agent in the workgroup.
+     *
+     * @param jid the XMPP address of the agent (eg "jsmith@example.com"). The
+     *            address can be in any valid format (e.g. "domain/resource", "user@domain"
+     *            or "user@domain/resource").
+     * @return true if the XMPP address is an agent in the workgroup.
+     */
+    public boolean contains(String jid) {
+        if (jid == null) {
+            return false;
+        }
+        synchronized (entries) {
+            for (Iterator<String> i = entries.iterator(); i.hasNext();) {
+                String entry = i.next();
+                if (entry.toLowerCase().equals(jid.toLowerCase())) {
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Returns the presence info for a particular agent, or <tt>null</tt> if the agent
+     * is unavailable (offline) or if no presence information is available.<p>
+     *
+     * @param user a fully qualified xmpp JID. The address could be in any valid format (e.g.
+     *             "domain/resource", "user@domain" or "user@domain/resource").
+     * @return the agent's current presence, or <tt>null</tt> if the agent is unavailable
+     *         or if no presence information is available..
+     */
+    public Presence getPresence(String user) {
+        String key = getPresenceMapKey(user);
+        Map<String, Presence> userPresences = presenceMap.get(key);
+        if (userPresences == null) {
+            Presence presence = new Presence(Presence.Type.unavailable);
+            presence.setFrom(user);
+            return presence;
+        }
+        else {
+            // Find the resource with the highest priority
+            // Might be changed to use the resource with the highest availability instead.
+            Iterator<String> it = userPresences.keySet().iterator();
+            Presence p;
+            Presence presence = null;
+
+            while (it.hasNext()) {
+                p = (Presence)userPresences.get(it.next());
+                if (presence == null){
+                    presence = p;
+                }
+                else {
+                    if (p.getPriority() > presence.getPriority()) {
+                        presence = p;
+                    }
+                }
+            }
+            if (presence == null) {
+                presence = new Presence(Presence.Type.unavailable);
+                presence.setFrom(user);
+                return presence;
+            }
+            else {
+                return presence;
+            }
+        }
+    }
+
+    /**
+     * Returns the key to use in the presenceMap for a fully qualified xmpp ID. The roster
+     * can contain any valid address format such us "domain/resource", "user@domain" or
+     * "user@domain/resource". If the roster contains an entry associated with the fully qualified
+     * xmpp ID then use the fully qualified xmpp ID as the key in presenceMap, otherwise use the
+     * bare address. Note: When the key in presenceMap is a fully qualified xmpp ID, the
+     * userPresences is useless since it will always contain one entry for the user.
+     *
+     * @param user the fully qualified xmpp ID, e.g. jdoe@example.com/Work.
+     * @return the key to use in the presenceMap for the fully qualified xmpp ID.
+     */
+    private String getPresenceMapKey(String user) {
+        String key = user;
+        if (!contains(user)) {
+            key = StringUtils.parseBareAddress(user).toLowerCase();
+        }
+        return key;
+    }
+
+    /**
+     * Fires event to listeners.
+     */
+    private void fireEvent(int eventType, Object eventObject) {
+        AgentRosterListener[] listeners = null;
+        synchronized (this.listeners) {
+            listeners = new AgentRosterListener[this.listeners.size()];
+            this.listeners.toArray(listeners);
+        }
+        for (int i = 0; i < listeners.length; i++) {
+            switch (eventType) {
+                case EVENT_AGENT_ADDED:
+                    listeners[i].agentAdded((String)eventObject);
+                    break;
+                case EVENT_AGENT_REMOVED:
+                    listeners[i].agentRemoved((String)eventObject);
+                    break;
+                case EVENT_PRESENCE_CHANGED:
+                    listeners[i].presenceChanged((Presence)eventObject);
+                    break;
+            }
+        }
+    }
+
+    /**
+     * Listens for all presence packets and processes them.
+     */
+    private class PresencePacketListener implements PacketListener {
+        public void processPacket(Packet packet) {
+            Presence presence = (Presence)packet;
+            String from = presence.getFrom();
+            if (from == null) {
+                // TODO Check if we need to ignore these presences or this is a server bug?
+                System.out.println("Presence with no FROM: " + presence.toXML());
+                return;
+            }
+            String key = getPresenceMapKey(from);
+
+            // If an "available" packet, add it to the presence map. Each presence map will hold
+            // for a particular user a map with the presence packets saved for each resource.
+            if (presence.getType() == Presence.Type.available) {
+                // Ignore the presence packet unless it has an agent status extension.
+                AgentStatus agentStatus = (AgentStatus)presence.getExtension(
+                        AgentStatus.ELEMENT_NAME, AgentStatus.NAMESPACE);
+                if (agentStatus == null) {
+                    return;
+                }
+                // Ensure that this presence is coming from an Agent of the same workgroup
+                // of this Agent
+                else if (!workgroupJID.equals(agentStatus.getWorkgroupJID())) {
+                    return;
+                }
+                Map<String, Presence> userPresences;
+                // Get the user presence map
+                if (presenceMap.get(key) == null) {
+                    userPresences = new HashMap<String, Presence>();
+                    presenceMap.put(key, userPresences);
+                }
+                else {
+                    userPresences = presenceMap.get(key);
+                }
+                // Add the new presence, using the resources as a key.
+                synchronized (userPresences) {
+                    userPresences.put(StringUtils.parseResource(from), presence);
+                }
+                // Fire an event.
+                synchronized (entries) {
+                    for (Iterator<String> i = entries.iterator(); i.hasNext();) {
+                        String entry = i.next();
+                        if (entry.toLowerCase().equals(StringUtils.parseBareAddress(key).toLowerCase())) {
+                            fireEvent(EVENT_PRESENCE_CHANGED, packet);
+                        }
+                    }
+                }
+            }
+            // If an "unavailable" packet, remove any entries in the presence map.
+            else if (presence.getType() == Presence.Type.unavailable) {
+                if (presenceMap.get(key) != null) {
+                    Map<String,Presence> userPresences = presenceMap.get(key);
+                    synchronized (userPresences) {
+                        userPresences.remove(StringUtils.parseResource(from));
+                    }
+                    if (userPresences.isEmpty()) {
+                        presenceMap.remove(key);
+                    }
+                }
+                // Fire an event.
+                synchronized (entries) {
+                    for (Iterator<String> i = entries.iterator(); i.hasNext();) {
+                        String entry = (String)i.next();
+                        if (entry.toLowerCase().equals(StringUtils.parseBareAddress(key).toLowerCase())) {
+                            fireEvent(EVENT_PRESENCE_CHANGED, packet);
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    /**
+     * Listens for all roster packets and processes them.
+     */
+    private class AgentStatusListener implements PacketListener {
+
+        public void processPacket(Packet packet) {
+            if (packet instanceof AgentStatusRequest) {
+                AgentStatusRequest statusRequest = (AgentStatusRequest)packet;
+                for (Iterator<AgentStatusRequest.Item> i = statusRequest.getAgents().iterator(); i.hasNext();) {
+                    AgentStatusRequest.Item item = i.next();
+                    String agentJID = item.getJID();
+                    if ("remove".equals(item.getType())) {
+
+                        // Removing the user from the roster, so remove any presence information
+                        // about them.
+                        String key = StringUtils.parseName(StringUtils.parseName(agentJID) + "@" +
+                                StringUtils.parseServer(agentJID));
+                        presenceMap.remove(key);
+                        // Fire event for roster listeners.
+                        fireEvent(EVENT_AGENT_REMOVED, agentJID);
+                    }
+                    else {
+                        entries.add(agentJID);
+                        // Fire event for roster listeners.
+                        fireEvent(EVENT_AGENT_ADDED, agentJID);
+                    }
+                }
+
+                // Mark the roster as initialized.
+                rosterInitialized = true;
+            }
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/AgentRosterListener.java b/src/org/jivesoftware/smackx/workgroup/agent/AgentRosterListener.java
new file mode 100644
index 0000000..4db9203
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/AgentRosterListener.java
@@ -0,0 +1,35 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smack.packet.Presence;
+
+/**
+ *
+ * @author Matt Tucker
+ */
+public interface AgentRosterListener {
+
+    public void agentAdded(String jid);
+
+    public void agentRemoved(String jid);
+
+    public void presenceChanged(Presence presence);
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/AgentSession.java b/src/org/jivesoftware/smackx/workgroup/agent/AgentSession.java
new file mode 100644
index 0000000..46d19d0
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/AgentSession.java
@@ -0,0 +1,1185 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smackx.workgroup.MetaData;
+import org.jivesoftware.smackx.workgroup.QueueUser;
+import org.jivesoftware.smackx.workgroup.WorkgroupInvitation;
+import org.jivesoftware.smackx.workgroup.WorkgroupInvitationListener;
+import org.jivesoftware.smackx.workgroup.ext.history.AgentChatHistory;
+import org.jivesoftware.smackx.workgroup.ext.history.ChatMetadata;
+import org.jivesoftware.smackx.workgroup.ext.macros.MacroGroup;
+import org.jivesoftware.smackx.workgroup.ext.macros.Macros;
+import org.jivesoftware.smackx.workgroup.ext.notes.ChatNotes;
+import org.jivesoftware.smackx.workgroup.packet.*;
+import org.jivesoftware.smackx.workgroup.settings.GenericSettings;
+import org.jivesoftware.smackx.workgroup.settings.SearchSettings;
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.filter.*;
+import org.jivesoftware.smack.packet.*;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.ReportedData;
+import org.jivesoftware.smackx.packet.MUCUser;
+
+import java.util.*;
+
+/**
+ * This class embodies the agent's active presence within a given workgroup. The application
+ * should have N instances of this class, where N is the number of workgroups to which the
+ * owning agent of the application belongs. This class provides all functionality that a
+ * session within a given workgroup is expected to have from an agent's perspective -- setting
+ * the status, tracking the status of queues to which the agent belongs within the workgroup, and
+ * dequeuing customers.
+ *
+ * @author Matt Tucker
+ * @author Derek DeMoro
+ */
+public class AgentSession {
+
+    private Connection connection;
+
+    private String workgroupJID;
+
+    private boolean online = false;
+    private Presence.Mode presenceMode;
+    private int maxChats;
+    private final Map<String, List<String>> metaData;
+
+    private Map<String, WorkgroupQueue> queues;
+
+    private final List<OfferListener> offerListeners;
+    private final List<WorkgroupInvitationListener> invitationListeners;
+    private final List<QueueUsersListener> queueUsersListeners;
+
+    private AgentRoster agentRoster = null;
+    private TranscriptManager transcriptManager;
+    private TranscriptSearchManager transcriptSearchManager;
+    private Agent agent;
+    private PacketListener packetListener;
+
+    /**
+     * Constructs a new agent session instance. Note, the {@link #setOnline(boolean)}
+     * method must be called with an argument of <tt>true</tt> to mark the agent
+     * as available to accept chat requests.
+     *
+     * @param connection   a connection instance which must have already gone through
+     *                     authentication.
+     * @param workgroupJID the fully qualified JID of the workgroup.
+     */
+    public AgentSession(String workgroupJID, Connection connection) {
+        // Login must have been done before passing in connection.
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Must login to server before creating workgroup.");
+        }
+
+        this.workgroupJID = workgroupJID;
+        this.connection = connection;
+        this.transcriptManager = new TranscriptManager(connection);
+        this.transcriptSearchManager = new TranscriptSearchManager(connection);
+
+        this.maxChats = -1;
+
+        this.metaData = new HashMap<String, List<String>>();
+
+        this.queues = new HashMap<String, WorkgroupQueue>();
+
+        offerListeners = new ArrayList<OfferListener>();
+        invitationListeners = new ArrayList<WorkgroupInvitationListener>();
+        queueUsersListeners = new ArrayList<QueueUsersListener>();
+
+        // Create a filter to listen for packets we're interested in.
+        OrFilter filter = new OrFilter();
+        filter.addFilter(new PacketTypeFilter(OfferRequestProvider.OfferRequestPacket.class));
+        filter.addFilter(new PacketTypeFilter(OfferRevokeProvider.OfferRevokePacket.class));
+        filter.addFilter(new PacketTypeFilter(Presence.class));
+        filter.addFilter(new PacketTypeFilter(Message.class));
+
+        packetListener = new PacketListener() {
+            public void processPacket(Packet packet) {
+                try {
+                    handlePacket(packet);
+                }
+                catch (Exception e) {
+                    e.printStackTrace();
+                }
+            }
+        };
+        connection.addPacketListener(packetListener, filter);
+        // Create the agent associated to this session
+        agent = new Agent(connection, workgroupJID);
+    }
+
+    /**
+     * Close the agent session. The underlying connection will remain opened but the
+     * packet listeners that were added by this agent session will be removed.
+     */
+    public void close() {
+        connection.removePacketListener(packetListener);
+    }
+
+    /**
+     * Returns the agent roster for the workgroup, which contains
+     *
+     * @return the AgentRoster
+     */
+    public AgentRoster getAgentRoster() {
+        if (agentRoster == null) {
+            agentRoster = new AgentRoster(connection, workgroupJID);
+        }
+
+        // This might be the first time the user has asked for the roster. If so, we
+        // want to wait up to 2 seconds for the server to send back the list of agents.
+        // This behavior shields API users from having to worry about the fact that the
+        // operation is asynchronous, although they'll still have to listen for changes
+        // to the roster.
+        int elapsed = 0;
+        while (!agentRoster.rosterInitialized && elapsed <= 2000) {
+            try {
+                Thread.sleep(500);
+            }
+            catch (Exception e) {
+                // Ignore
+            }
+            elapsed += 500;
+        }
+        return agentRoster;
+    }
+
+    /**
+     * Returns the agent's current presence mode.
+     *
+     * @return the agent's current presence mode.
+     */
+    public Presence.Mode getPresenceMode() {
+        return presenceMode;
+    }
+
+    /**
+     * Returns the maximum number of chats the agent can participate in.
+     *
+     * @return the maximum number of chats the agent can participate in.
+     */
+    public int getMaxChats() {
+        return maxChats;
+    }
+
+    /**
+     * Returns true if the agent is online with the workgroup.
+     *
+     * @return true if the agent is online with the workgroup.
+     */
+    public boolean isOnline() {
+        return online;
+    }
+
+    /**
+     * Allows the addition of a new key-value pair to the agent's meta data, if the value is
+     * new data, the revised meta data will be rebroadcast in an agent's presence broadcast.
+     *
+     * @param key the meta data key
+     * @param val the non-null meta data value
+     * @throws XMPPException if an exception occurs.
+     */
+    public void setMetaData(String key, String val) throws XMPPException {
+        synchronized (this.metaData) {
+            List<String> oldVals = metaData.get(key);
+
+            if ((oldVals == null) || (!oldVals.get(0).equals(val))) {
+                oldVals.set(0, val);
+
+                setStatus(presenceMode, maxChats);
+            }
+        }
+    }
+
+    /**
+     * Allows the removal of data from the agent's meta data, if the key represents existing data,
+     * the revised meta data will be rebroadcast in an agent's presence broadcast.
+     *
+     * @param key the meta data key.
+     * @throws XMPPException if an exception occurs.
+     */
+    public void removeMetaData(String key) throws XMPPException {
+        synchronized (this.metaData) {
+            List<String> oldVal = metaData.remove(key);
+
+            if (oldVal != null) {
+                setStatus(presenceMode, maxChats);
+            }
+        }
+    }
+
+    /**
+     * Allows the retrieval of meta data for a specified key.
+     *
+     * @param key the meta data key
+     * @return the meta data value associated with the key or <tt>null</tt> if the meta-data
+     *         doesn't exist..
+     */
+    public List<String> getMetaData(String key) {
+        return metaData.get(key);
+    }
+
+    /**
+     * Sets whether the agent is online with the workgroup. If the user tries to go online with
+     * the workgroup but is not allowed to be an agent, an XMPPError with error code 401 will
+     * be thrown.
+     *
+     * @param online true to set the agent as online with the workgroup.
+     * @throws XMPPException if an error occurs setting the online status.
+     */
+    public void setOnline(boolean online) throws XMPPException {
+        // If the online status hasn't changed, do nothing.
+        if (this.online == online) {
+            return;
+        }
+
+        Presence presence;
+
+        // If the user is going online...
+        if (online) {
+            presence = new Presence(Presence.Type.available);
+            presence.setTo(workgroupJID);
+            presence.addExtension(new DefaultPacketExtension(AgentStatus.ELEMENT_NAME,
+                    AgentStatus.NAMESPACE));
+
+            PacketCollector collector = this.connection.createPacketCollector(new AndFilter(new PacketTypeFilter(Presence.class), new FromContainsFilter(workgroupJID)));
+
+            connection.sendPacket(presence);
+
+            presence = (Presence)collector.nextResult(5000);
+            collector.cancel();
+            if (!presence.isAvailable()) {
+                throw new XMPPException("No response from server on status set.");
+            }
+
+            if (presence.getError() != null) {
+                throw new XMPPException(presence.getError());
+            }
+
+            // We can safely update this iv since we didn't get any error
+            this.online = online;
+        }
+        // Otherwise the user is going offline...
+        else {
+            // Update this iv now since we don't care at this point of any error
+            this.online = online;
+
+            presence = new Presence(Presence.Type.unavailable);
+            presence.setTo(workgroupJID);
+            presence.addExtension(new DefaultPacketExtension(AgentStatus.ELEMENT_NAME,
+                    AgentStatus.NAMESPACE));
+            connection.sendPacket(presence);
+        }
+    }
+
+    /**
+     * Sets the agent's current status with the workgroup. The presence mode affects
+     * how offers are routed to the agent. The possible presence modes with their
+     * meanings are as follows:<ul>
+     * <p/>
+     * <li>Presence.Mode.AVAILABLE -- (Default) the agent is available for more chats
+     * (equivalent to Presence.Mode.CHAT).
+     * <li>Presence.Mode.DO_NOT_DISTURB -- the agent is busy and should not be disturbed.
+     * However, special case, or extreme urgency chats may still be offered to the agent.
+     * <li>Presence.Mode.AWAY -- the agent is not available and should not
+     * have a chat routed to them (equivalent to Presence.Mode.EXTENDED_AWAY).</ul>
+     * <p/>
+     * The max chats value is the maximum number of chats the agent is willing to have
+     * routed to them at once. Some servers may be configured to only accept max chat
+     * values in a certain range; for example, between two and five. In that case, the
+     * maxChats value the agent sends may be adjusted by the server to a value within that
+     * range.
+     *
+     * @param presenceMode the presence mode of the agent.
+     * @param maxChats     the maximum number of chats the agent is willing to accept.
+     * @throws XMPPException         if an error occurs setting the agent status.
+     * @throws IllegalStateException if the agent is not online with the workgroup.
+     */
+    public void setStatus(Presence.Mode presenceMode, int maxChats) throws XMPPException {
+        setStatus(presenceMode, maxChats, null);
+    }
+
+    /**
+     * Sets the agent's current status with the workgroup. The presence mode affects how offers
+     * are routed to the agent. The possible presence modes with their meanings are as follows:<ul>
+     * <p/>
+     * <li>Presence.Mode.AVAILABLE -- (Default) the agent is available for more chats
+     * (equivalent to Presence.Mode.CHAT).
+     * <li>Presence.Mode.DO_NOT_DISTURB -- the agent is busy and should not be disturbed.
+     * However, special case, or extreme urgency chats may still be offered to the agent.
+     * <li>Presence.Mode.AWAY -- the agent is not available and should not
+     * have a chat routed to them (equivalent to Presence.Mode.EXTENDED_AWAY).</ul>
+     * <p/>
+     * The max chats value is the maximum number of chats the agent is willing to have routed to
+     * them at once. Some servers may be configured to only accept max chat values in a certain
+     * range; for example, between two and five. In that case, the maxChats value the agent sends
+     * may be adjusted by the server to a value within that range.
+     *
+     * @param presenceMode the presence mode of the agent.
+     * @param maxChats     the maximum number of chats the agent is willing to accept.
+     * @param status       sets the status message of the presence update.
+     * @throws XMPPException         if an error occurs setting the agent status.
+     * @throws IllegalStateException if the agent is not online with the workgroup.
+     */
+    public void setStatus(Presence.Mode presenceMode, int maxChats, String status)
+            throws XMPPException {
+        if (!online) {
+            throw new IllegalStateException("Cannot set status when the agent is not online.");
+        }
+
+        if (presenceMode == null) {
+            presenceMode = Presence.Mode.available;
+        }
+        this.presenceMode = presenceMode;
+        this.maxChats = maxChats;
+
+        Presence presence = new Presence(Presence.Type.available);
+        presence.setMode(presenceMode);
+        presence.setTo(this.getWorkgroupJID());
+
+        if (status != null) {
+            presence.setStatus(status);
+        }
+        // Send information about max chats and current chats as a packet extension.
+        DefaultPacketExtension agentStatus = new DefaultPacketExtension(AgentStatus.ELEMENT_NAME,
+                AgentStatus.NAMESPACE);
+        agentStatus.setValue("max-chats", "" + maxChats);
+        presence.addExtension(agentStatus);
+        presence.addExtension(new MetaData(this.metaData));
+
+        PacketCollector collector = this.connection.createPacketCollector(new AndFilter(new PacketTypeFilter(Presence.class), new FromContainsFilter(workgroupJID)));
+
+        this.connection.sendPacket(presence);
+
+        presence = (Presence)collector.nextResult(5000);
+        collector.cancel();
+        if (!presence.isAvailable()) {
+            throw new XMPPException("No response from server on status set.");
+        }
+
+        if (presence.getError() != null) {
+            throw new XMPPException(presence.getError());
+        }
+    }
+
+    /**
+     * Sets the agent's current status with the workgroup. The presence mode affects how offers
+     * are routed to the agent. The possible presence modes with their meanings are as follows:<ul>
+     * <p/>
+     * <li>Presence.Mode.AVAILABLE -- (Default) the agent is available for more chats
+     * (equivalent to Presence.Mode.CHAT).
+     * <li>Presence.Mode.DO_NOT_DISTURB -- the agent is busy and should not be disturbed.
+     * However, special case, or extreme urgency chats may still be offered to the agent.
+     * <li>Presence.Mode.AWAY -- the agent is not available and should not
+     * have a chat routed to them (equivalent to Presence.Mode.EXTENDED_AWAY).</ul>
+     *
+     * @param presenceMode the presence mode of the agent.
+     * @param status       sets the status message of the presence update.
+     * @throws XMPPException         if an error occurs setting the agent status.
+     * @throws IllegalStateException if the agent is not online with the workgroup.
+     */
+    public void setStatus(Presence.Mode presenceMode, String status) throws XMPPException {
+        if (!online) {
+            throw new IllegalStateException("Cannot set status when the agent is not online.");
+        }
+
+        if (presenceMode == null) {
+            presenceMode = Presence.Mode.available;
+        }
+        this.presenceMode = presenceMode;
+
+        Presence presence = new Presence(Presence.Type.available);
+        presence.setMode(presenceMode);
+        presence.setTo(this.getWorkgroupJID());
+
+        if (status != null) {
+            presence.setStatus(status);
+        }
+        presence.addExtension(new MetaData(this.metaData));
+
+        PacketCollector collector = this.connection.createPacketCollector(new AndFilter(new PacketTypeFilter(Presence.class),
+                new FromContainsFilter(workgroupJID)));
+
+        this.connection.sendPacket(presence);
+
+        presence = (Presence)collector.nextResult(5000);
+        collector.cancel();
+        if (!presence.isAvailable()) {
+            throw new XMPPException("No response from server on status set.");
+        }
+
+        if (presence.getError() != null) {
+            throw new XMPPException(presence.getError());
+        }
+    }
+
+    /**
+     * Removes a user from the workgroup queue. This is an administrative action that the
+     * <p/>
+     * The agent is not guaranteed of having privileges to perform this action; an exception
+     * denying the request may be thrown.
+     *
+     * @param userID the ID of the user to remove.
+     * @throws XMPPException if an exception occurs.
+     */
+    public void dequeueUser(String userID) throws XMPPException {
+        // todo: this method simply won't work right now.
+        DepartQueuePacket departPacket = new DepartQueuePacket(this.workgroupJID);
+
+        // PENDING
+        this.connection.sendPacket(departPacket);
+    }
+
+    /**
+     * Returns the transcripts of a given user. The answer will contain the complete history of
+     * conversations that a user had.
+     *
+     * @param userID the id of the user to get his conversations.
+     * @return the transcripts of a given user.
+     * @throws XMPPException if an error occurs while getting the information.
+     */
+    public Transcripts getTranscripts(String userID) throws XMPPException {
+        return transcriptManager.getTranscripts(workgroupJID, userID);
+    }
+
+    /**
+     * Returns the full conversation transcript of a given session.
+     *
+     * @param sessionID the id of the session to get the full transcript.
+     * @return the full conversation transcript of a given session.
+     * @throws XMPPException if an error occurs while getting the information.
+     */
+    public Transcript getTranscript(String sessionID) throws XMPPException {
+        return transcriptManager.getTranscript(workgroupJID, sessionID);
+    }
+
+    /**
+     * Returns the Form to use for searching transcripts. It is unlikely that the server
+     * will change the form (without a restart) so it is safe to keep the returned form
+     * for future submissions.
+     *
+     * @return the Form to use for searching transcripts.
+     * @throws XMPPException if an error occurs while sending the request to the server.
+     */
+    public Form getTranscriptSearchForm() throws XMPPException {
+        return transcriptSearchManager.getSearchForm(StringUtils.parseServer(workgroupJID));
+    }
+
+    /**
+     * Submits the completed form and returns the result of the transcript search. The result
+     * will include all the data returned from the server so be careful with the amount of
+     * data that the search may return.
+     *
+     * @param completedForm the filled out search form.
+     * @return the result of the transcript search.
+     * @throws XMPPException if an error occurs while submiting the search to the server.
+     */
+    public ReportedData searchTranscripts(Form completedForm) throws XMPPException {
+        return transcriptSearchManager.submitSearch(StringUtils.parseServer(workgroupJID),
+                completedForm);
+    }
+
+    /**
+     * Asks the workgroup for information about the occupants of the specified room. The returned
+     * information will include the real JID of the occupants, the nickname of the user in the
+     * room as well as the date when the user joined the room.
+     *
+     * @param roomID the room to get information about its occupants.
+     * @return information about the occupants of the specified room.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public OccupantsInfo getOccupantsInfo(String roomID) throws XMPPException {
+        OccupantsInfo request = new OccupantsInfo(roomID);
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+        OccupantsInfo response = (OccupantsInfo)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * @return the fully-qualified name of the workgroup for which this session exists
+     */
+    public String getWorkgroupJID() {
+        return workgroupJID;
+    }
+
+    /**
+     * Returns the Agent associated to this session.
+     *
+     * @return the Agent associated to this session.
+     */
+    public Agent getAgent() {
+        return agent;
+    }
+
+    /**
+     * @param queueName the name of the queue
+     * @return an instance of WorkgroupQueue for the argument queue name, or null if none exists
+     */
+    public WorkgroupQueue getQueue(String queueName) {
+        return queues.get(queueName);
+    }
+
+    public Iterator<WorkgroupQueue> getQueues() {
+        return Collections.unmodifiableMap((new HashMap<String, WorkgroupQueue>(queues))).values().iterator();
+    }
+
+    public void addQueueUsersListener(QueueUsersListener listener) {
+        synchronized (queueUsersListeners) {
+            if (!queueUsersListeners.contains(listener)) {
+                queueUsersListeners.add(listener);
+            }
+        }
+    }
+
+    public void removeQueueUsersListener(QueueUsersListener listener) {
+        synchronized (queueUsersListeners) {
+            queueUsersListeners.remove(listener);
+        }
+    }
+
+    /**
+     * Adds an offer listener.
+     *
+     * @param offerListener the offer listener.
+     */
+    public void addOfferListener(OfferListener offerListener) {
+        synchronized (offerListeners) {
+            if (!offerListeners.contains(offerListener)) {
+                offerListeners.add(offerListener);
+            }
+        }
+    }
+
+    /**
+     * Removes an offer listener.
+     *
+     * @param offerListener the offer listener.
+     */
+    public void removeOfferListener(OfferListener offerListener) {
+        synchronized (offerListeners) {
+            offerListeners.remove(offerListener);
+        }
+    }
+
+    /**
+     * Adds an invitation listener.
+     *
+     * @param invitationListener the invitation listener.
+     */
+    public void addInvitationListener(WorkgroupInvitationListener invitationListener) {
+        synchronized (invitationListeners) {
+            if (!invitationListeners.contains(invitationListener)) {
+                invitationListeners.add(invitationListener);
+            }
+        }
+    }
+
+    /**
+     * Removes an invitation listener.
+     *
+     * @param invitationListener the invitation listener.
+     */
+    public void removeInvitationListener(WorkgroupInvitationListener invitationListener) {
+        synchronized (invitationListeners) {
+            invitationListeners.remove(invitationListener);
+        }
+    }
+
+    private void fireOfferRequestEvent(OfferRequestProvider.OfferRequestPacket requestPacket) {
+        Offer offer = new Offer(this.connection, this, requestPacket.getUserID(),
+                requestPacket.getUserJID(), this.getWorkgroupJID(),
+                new Date((new Date()).getTime() + (requestPacket.getTimeout() * 1000)),
+                requestPacket.getSessionID(), requestPacket.getMetaData(), requestPacket.getContent());
+
+        synchronized (offerListeners) {
+            for (OfferListener listener : offerListeners) {
+                listener.offerReceived(offer);
+            }
+        }
+    }
+
+    private void fireOfferRevokeEvent(OfferRevokeProvider.OfferRevokePacket orp) {
+        RevokedOffer revokedOffer = new RevokedOffer(orp.getUserJID(), orp.getUserID(),
+                this.getWorkgroupJID(), orp.getSessionID(), orp.getReason(), new Date());
+
+        synchronized (offerListeners) {
+            for (OfferListener listener : offerListeners) {
+                listener.offerRevoked(revokedOffer);
+            }
+        }
+    }
+
+    private void fireInvitationEvent(String groupChatJID, String sessionID, String body,
+                                     String from, Map<String, List<String>> metaData) {
+        WorkgroupInvitation invitation = new WorkgroupInvitation(connection.getUser(), groupChatJID,
+                workgroupJID, sessionID, body, from, metaData);
+
+        synchronized (invitationListeners) {
+            for (WorkgroupInvitationListener listener : invitationListeners) {
+                listener.invitationReceived(invitation);
+            }
+        }
+    }
+
+    private void fireQueueUsersEvent(WorkgroupQueue queue, WorkgroupQueue.Status status,
+                                     int averageWaitTime, Date oldestEntry, Set<QueueUser> users) {
+        synchronized (queueUsersListeners) {
+            for (QueueUsersListener listener : queueUsersListeners) {
+                if (status != null) {
+                    listener.statusUpdated(queue, status);
+                }
+                if (averageWaitTime != -1) {
+                    listener.averageWaitTimeUpdated(queue, averageWaitTime);
+                }
+                if (oldestEntry != null) {
+                    listener.oldestEntryUpdated(queue, oldestEntry);
+                }
+                if (users != null) {
+                    listener.usersUpdated(queue, users);
+                }
+            }
+        }
+    }
+
+    // PacketListener Implementation.
+
+    private void handlePacket(Packet packet) {
+        if (packet instanceof OfferRequestProvider.OfferRequestPacket) {
+            // Acknowledge the IQ set.
+            IQ reply = new IQ() {
+                public String getChildElementXML() {
+                    return null;
+                }
+            };
+            reply.setPacketID(packet.getPacketID());
+            reply.setTo(packet.getFrom());
+            reply.setType(IQ.Type.RESULT);
+            connection.sendPacket(reply);
+
+            fireOfferRequestEvent((OfferRequestProvider.OfferRequestPacket)packet);
+        }
+        else if (packet instanceof Presence) {
+            Presence presence = (Presence)packet;
+
+            // The workgroup can send us a number of different presence packets. We
+            // check for different packet extensions to see what type of presence
+            // packet it is.
+
+            String queueName = StringUtils.parseResource(presence.getFrom());
+            WorkgroupQueue queue = queues.get(queueName);
+            // If there isn't already an entry for the queue, create a new one.
+            if (queue == null) {
+                queue = new WorkgroupQueue(queueName);
+                queues.put(queueName, queue);
+            }
+
+            // QueueOverview packet extensions contain basic information about a queue.
+            QueueOverview queueOverview = (QueueOverview)presence.getExtension(QueueOverview.ELEMENT_NAME, QueueOverview.NAMESPACE);
+            if (queueOverview != null) {
+                if (queueOverview.getStatus() == null) {
+                    queue.setStatus(WorkgroupQueue.Status.CLOSED);
+                }
+                else {
+                    queue.setStatus(queueOverview.getStatus());
+                }
+                queue.setAverageWaitTime(queueOverview.getAverageWaitTime());
+                queue.setOldestEntry(queueOverview.getOldestEntry());
+                // Fire event.
+                fireQueueUsersEvent(queue, queueOverview.getStatus(),
+                        queueOverview.getAverageWaitTime(), queueOverview.getOldestEntry(),
+                        null);
+                return;
+            }
+
+            // QueueDetails packet extensions contain information about the users in
+            // a queue.
+            QueueDetails queueDetails = (QueueDetails)packet.getExtension(QueueDetails.ELEMENT_NAME, QueueDetails.NAMESPACE);
+            if (queueDetails != null) {
+                queue.setUsers(queueDetails.getUsers());
+                // Fire event.
+                fireQueueUsersEvent(queue, null, -1, null, queueDetails.getUsers());
+                return;
+            }
+
+            // Notify agent packets gives an overview of agent activity in a queue.
+            DefaultPacketExtension notifyAgents = (DefaultPacketExtension)presence.getExtension("notify-agents", "http://jabber.org/protocol/workgroup");
+            if (notifyAgents != null) {
+                int currentChats = Integer.parseInt(notifyAgents.getValue("current-chats"));
+                int maxChats = Integer.parseInt(notifyAgents.getValue("max-chats"));
+                queue.setCurrentChats(currentChats);
+                queue.setMaxChats(maxChats);
+                // Fire event.
+                // TODO: might need another event for current chats and max chats of queue
+                return;
+            }
+        }
+        else if (packet instanceof Message) {
+            Message message = (Message)packet;
+
+            // Check if a room invitation was sent and if the sender is the workgroup
+            MUCUser mucUser = (MUCUser)message.getExtension("x",
+                    "http://jabber.org/protocol/muc#user");
+            MUCUser.Invite invite = mucUser != null ? mucUser.getInvite() : null;
+            if (invite != null && workgroupJID.equals(invite.getFrom())) {
+                String sessionID = null;
+                Map<String, List<String>> metaData = null;
+
+                SessionID sessionIDExt = (SessionID)message.getExtension(SessionID.ELEMENT_NAME,
+                        SessionID.NAMESPACE);
+                if (sessionIDExt != null) {
+                    sessionID = sessionIDExt.getSessionID();
+                }
+
+                MetaData metaDataExt = (MetaData)message.getExtension(MetaData.ELEMENT_NAME,
+                        MetaData.NAMESPACE);
+                if (metaDataExt != null) {
+                    metaData = metaDataExt.getMetaData();
+                }
+
+                this.fireInvitationEvent(message.getFrom(), sessionID, message.getBody(),
+                        message.getFrom(), metaData);
+            }
+        }
+        else if (packet instanceof OfferRevokeProvider.OfferRevokePacket) {
+            // Acknowledge the IQ set.
+            IQ reply = new IQ() {
+                public String getChildElementXML() {
+                    return null;
+                }
+            };
+            reply.setPacketID(packet.getPacketID());
+            reply.setType(IQ.Type.RESULT);
+            connection.sendPacket(reply);
+
+            fireOfferRevokeEvent((OfferRevokeProvider.OfferRevokePacket)packet);
+        }
+    }
+
+    /**
+     * Creates a ChatNote that will be mapped to the given chat session.
+     *
+     * @param sessionID the session id of a Chat Session.
+     * @param note      the chat note to add.
+     * @throws XMPPException is thrown if an error occurs while adding the note.
+     */
+    public void setNote(String sessionID, String note) throws XMPPException {
+        note = ChatNotes.replace(note, "\n", "\\n");
+        note = StringUtils.escapeForXML(note);
+
+        ChatNotes notes = new ChatNotes();
+        notes.setType(IQ.Type.SET);
+        notes.setTo(workgroupJID);
+        notes.setSessionID(sessionID);
+        notes.setNotes(note);
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(notes.getPacketID()));
+        // Send the request
+        connection.sendPacket(notes);
+
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Retrieves the ChatNote associated with a given chat session.
+     *
+     * @param sessionID the sessionID of the chat session.
+     * @return the <code>ChatNote</code> associated with a given chat session.
+     * @throws XMPPException if an error occurs while retrieving the ChatNote.
+     */
+    public ChatNotes getNote(String sessionID) throws XMPPException {
+        ChatNotes request = new ChatNotes();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+        request.setSessionID(sessionID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+        ChatNotes response = (ChatNotes)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+
+    }
+
+    /**
+     * Retrieves the AgentChatHistory associated with a particular agent jid.
+     *
+     * @param jid the jid of the agent.
+     * @param maxSessions the max number of sessions to retrieve.
+     * @param startDate the starting date of sessions to retrieve.
+     * @return the chat history associated with a given jid.
+     * @throws XMPPException if an error occurs while retrieving the AgentChatHistory.
+     */
+    public AgentChatHistory getAgentHistory(String jid, int maxSessions, Date startDate) throws XMPPException {
+        AgentChatHistory request;
+        if (startDate != null) {
+            request = new AgentChatHistory(jid, maxSessions, startDate);
+        }
+        else {
+            request = new AgentChatHistory(jid, maxSessions);
+        }
+
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+        AgentChatHistory response = (AgentChatHistory)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Asks the workgroup for it's Search Settings.
+     *
+     * @return SearchSettings the search settings for this workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public SearchSettings getSearchSettings() throws XMPPException {
+        SearchSettings request = new SearchSettings();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        SearchSettings response = (SearchSettings)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Asks the workgroup for it's Global Macros.
+     *
+     * @param global true to retrieve global macros, otherwise false for personal macros.
+     * @return MacroGroup the root macro group.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public MacroGroup getMacros(boolean global) throws XMPPException {
+        Macros request = new Macros();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+        request.setPersonal(!global);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        Macros response = (Macros)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response.getRootGroup();
+    }
+
+    /**
+     * Persists the Personal Macro for an agent.
+     *
+     * @param group the macro group to save. 
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public void saveMacros(MacroGroup group) throws XMPPException {
+        Macros request = new Macros();
+        request.setType(IQ.Type.SET);
+        request.setTo(workgroupJID);
+        request.setPersonal(true);
+        request.setPersonalMacroGroup(group);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Query for metadata associated with a session id.
+     *
+     * @param sessionID the sessionID to query for.
+     * @return Map a map of all metadata associated with the sessionID.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public Map<String, List<String>> getChatMetadata(String sessionID) throws XMPPException {
+        ChatMetadata request = new ChatMetadata();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+        request.setSessionID(sessionID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        ChatMetadata response = (ChatMetadata)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response.getMetadata();
+    }
+
+    /**
+     * Invites a user or agent to an existing session support. The provided invitee's JID can be of
+     * a user, an agent, a queue or a workgroup. In the case of a queue or a workgroup the workgroup service
+     * will decide the best agent to receive the invitation.<p>
+     *
+     * This method will return either when the service returned an ACK of the request or if an error occured
+     * while requesting the invitation. After sending the ACK the service will send the invitation to the target
+     * entity. When dealing with agents the common sequence of offer-response will be followed. However, when
+     * sending an invitation to a user a standard MUC invitation will be sent.<p>
+     *
+     * The agent or user that accepted the offer <b>MUST</b> join the room. Failing to do so will make
+     * the invitation to fail. The inviter will eventually receive a message error indicating that the invitee
+     * accepted the offer but failed to join the room.
+     *
+     * Different situations may lead to a failed invitation. Possible cases are: 1) all agents rejected the
+     * offer and ther are no agents available, 2) the agent that accepted the offer failed to join the room or
+     * 2) the user that received the MUC invitation never replied or joined the room. In any of these cases
+     * (or other failing cases) the inviter will get an error message with the failed notification.
+     *
+     * @param type type of entity that will get the invitation.
+     * @param invitee JID of entity that will get the invitation.
+     * @param sessionID ID of the support session that the invitee is being invited.
+     * @param reason the reason of the invitation.
+     * @throws XMPPException if the sender of the invitation is not an agent or the service failed to process
+     *         the request.
+     */
+    public void sendRoomInvitation(RoomInvitation.Type type, String invitee, String sessionID, String reason)
+            throws XMPPException {
+        final RoomInvitation invitation = new RoomInvitation(type, invitee, sessionID, reason);
+        IQ iq = new IQ() {
+
+            public String getChildElementXML() {
+                return invitation.toXML();
+            }
+        };
+        iq.setType(IQ.Type.SET);
+        iq.setTo(workgroupJID);
+        iq.setFrom(connection.getUser());
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(iq.getPacketID()));
+        connection.sendPacket(iq);
+
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Transfer an existing session support to another user or agent. The provided invitee's JID can be of
+     * a user, an agent, a queue or a workgroup. In the case of a queue or a workgroup the workgroup service
+     * will decide the best agent to receive the invitation.<p>
+     *
+     * This method will return either when the service returned an ACK of the request or if an error occured
+     * while requesting the transfer. After sending the ACK the service will send the invitation to the target
+     * entity. When dealing with agents the common sequence of offer-response will be followed. However, when
+     * sending an invitation to a user a standard MUC invitation will be sent.<p>
+     *
+     * Once the invitee joins the support room the workgroup service will kick the inviter from the room.<p>
+     *
+     * Different situations may lead to a failed transfers. Possible cases are: 1) all agents rejected the
+     * offer and there are no agents available, 2) the agent that accepted the offer failed to join the room
+     * or 2) the user that received the MUC invitation never replied or joined the room. In any of these cases
+     * (or other failing cases) the inviter will get an error message with the failed notification.
+     *
+     * @param type type of entity that will get the invitation.
+     * @param invitee JID of entity that will get the invitation.
+     * @param sessionID ID of the support session that the invitee is being invited.
+     * @param reason the reason of the invitation.
+     * @throws XMPPException if the sender of the invitation is not an agent or the service failed to process
+     *         the request.
+     */
+    public void sendRoomTransfer(RoomTransfer.Type type, String invitee, String sessionID, String reason)
+            throws XMPPException {
+        final RoomTransfer transfer = new RoomTransfer(type, invitee, sessionID, reason);
+        IQ iq = new IQ() {
+
+            public String getChildElementXML() {
+                return transfer.toXML();
+            }
+        };
+        iq.setType(IQ.Type.SET);
+        iq.setTo(workgroupJID);
+        iq.setFrom(connection.getUser());
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(iq.getPacketID()));
+        connection.sendPacket(iq);
+
+        IQ response = (IQ)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+
+    /**
+     * Returns the generic metadata of the workgroup the agent belongs to.
+     *
+     * @param con   the Connection to use.
+     * @param query an optional query object used to tell the server what metadata to retrieve. This can be null.
+     * @throws XMPPException if an error occurs while sending the request to the server.
+     * @return the settings for the workgroup.
+     */
+    public GenericSettings getGenericSettings(Connection con, String query) throws XMPPException {
+        GenericSettings setting = new GenericSettings();
+        setting.setType(IQ.Type.GET);
+        setting.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(setting.getPacketID()));
+        connection.sendPacket(setting);
+
+        GenericSettings response = (GenericSettings)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    public boolean hasMonitorPrivileges(Connection con) throws XMPPException {
+        MonitorPacket request = new MonitorPacket();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+        MonitorPacket response = (MonitorPacket)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response.isMonitor();
+
+    }
+
+    public void makeRoomOwner(Connection con, String sessionID) throws XMPPException {
+        MonitorPacket request = new MonitorPacket();
+        request.setType(IQ.Type.SET);
+        request.setTo(workgroupJID);
+        request.setSessionID(sessionID);
+
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+        Packet response = collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/InvitationRequest.java b/src/org/jivesoftware/smackx/workgroup/agent/InvitationRequest.java
new file mode 100644
index 0000000..16b324a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/InvitationRequest.java
@@ -0,0 +1,62 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+/**
+ * Request sent by an agent to invite another agent or user.
+ *
+ * @author Gaston Dombiak
+ */
+public class InvitationRequest extends OfferContent {
+
+    private String inviter;
+    private String room;
+    private String reason;
+
+    public InvitationRequest(String inviter, String room, String reason) {
+        this.inviter = inviter;
+        this.room = room;
+        this.reason = reason;
+    }
+
+    public String getInviter() {
+        return inviter;
+    }
+
+    public String getRoom() {
+        return room;
+    }
+
+    public String getReason() {
+        return reason;
+    }
+
+    boolean isUserRequest() {
+        return false;
+    }
+
+    boolean isInvitation() {
+        return true;
+    }
+
+    boolean isTransfer() {
+        return false;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/Offer.java b/src/org/jivesoftware/smackx/workgroup/agent/Offer.java
new file mode 100644
index 0000000..ece8c6f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/Offer.java
@@ -0,0 +1,223 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * A class embodying the semantic agent chat offer; specific instances allow the acceptance or
+ * rejecting of the offer.<br>
+ *
+ * @author Matt Tucker
+ * @author loki der quaeler
+ * @author Derek DeMoro
+ */
+public class Offer {
+
+    private Connection connection;
+    private AgentSession session;
+
+    private String sessionID;
+    private String userJID;
+    private String userID;
+    private String workgroupName;
+    private Date expiresDate;
+    private Map<String, List<String>> metaData;
+    private OfferContent content;
+
+    private boolean accepted = false;
+    private boolean rejected = false;
+
+    /**
+     * Creates a new offer.
+     *
+     * @param conn the XMPP connection with which the issuing session was created.
+     * @param agentSession the agent session instance through which this offer was issued.
+     * @param userID  the userID of the user from which the offer originates.
+     * @param userJID the XMPP address of the user from which the offer originates.
+     * @param workgroupName the fully qualified name of the workgroup.
+     * @param expiresDate the date at which this offer expires.
+     * @param sessionID the session id associated with the offer.
+     * @param metaData the metadata associated with the offer.
+     * @param content content of the offer. The content explains the reason for the offer
+     *        (e.g. user request, transfer)
+     */
+    Offer(Connection conn, AgentSession agentSession, String userID,
+            String userJID, String workgroupName, Date expiresDate,
+            String sessionID, Map<String, List<String>> metaData, OfferContent content)
+    {
+        this.connection = conn;
+        this.session = agentSession;
+        this.userID = userID;
+        this.userJID = userJID;
+        this.workgroupName = workgroupName;
+        this.expiresDate = expiresDate;
+        this.sessionID = sessionID;
+        this.metaData = metaData;
+        this.content = content;
+    }
+
+    /**
+     * Accepts the offer.
+     */
+    public void accept() {
+        Packet acceptPacket = new AcceptPacket(this.session.getWorkgroupJID());
+        connection.sendPacket(acceptPacket);
+        // TODO: listen for a reply.
+        accepted = true;
+    }
+
+    /**
+     * Rejects the offer.
+     */
+    public void reject() {
+        RejectPacket rejectPacket = new RejectPacket(this.session.getWorkgroupJID());
+        connection.sendPacket(rejectPacket);
+        // TODO: listen for a reply.
+        rejected = true;
+    }
+
+    /**
+     * Returns the userID that the offer originates from. In most cases, the
+     * userID will simply be the JID of the requesting user. However, users can
+     * also manually specify a userID for their request. In that case, that value will
+     * be returned.
+     *
+     * @return the userID of the user from which the offer originates.
+     */
+    public String getUserID() {
+        return userID;
+    }
+
+    /**
+     * Returns the JID of the user that made the offer request.
+     *
+     * @return the user's JID.
+     */
+    public String getUserJID() {
+        return userJID;
+    }
+
+    /**
+     * The fully qualified name of the workgroup (eg support@example.com).
+     *
+     * @return the name of the workgroup.
+     */
+    public String getWorkgroupName() {
+        return this.workgroupName;
+    }
+
+    /**
+     * The date when the offer will expire. The agent must {@link #accept()}
+     * the offer before the expiration date or the offer will lapse and be
+     * routed to another agent. Alternatively, the agent can {@link #reject()}
+     * the offer at any time if they don't wish to accept it..
+     *
+     * @return the date at which this offer expires.
+     */
+    public Date getExpiresDate() {
+        return this.expiresDate;
+    }
+
+    /**
+     * The session ID associated with the offer.
+     *
+     * @return the session id associated with the offer.
+     */
+    public String getSessionID() {
+        return this.sessionID;
+    }
+
+    /**
+     * The meta-data associated with the offer.
+     *
+     * @return the offer meta-data.
+     */
+    public Map<String, List<String>> getMetaData() {
+        return this.metaData;
+    }
+
+    /**
+     * Returns the content of the offer. The content explains the reason for the offer
+     * (e.g. user request, transfer)
+     *
+     * @return the content of the offer.
+     */
+    public OfferContent getContent() {
+        return content;
+    }
+
+    /**
+     * Returns true if the agent accepted this offer.
+     *
+     * @return true if the agent accepted this offer.
+     */
+    public boolean isAccepted() {
+        return accepted;
+    }
+
+    /**
+     * Return true if the agent rejected this offer.
+     *
+     * @return true if the agent rejected this offer.
+     */
+    public boolean isRejected() {
+        return rejected;
+    }
+
+    /**
+     * Packet for rejecting offers.
+     */
+    private class RejectPacket extends IQ {
+
+        RejectPacket(String workgroup) {
+            this.setTo(workgroup);
+            this.setType(IQ.Type.SET);
+        }
+
+        public String getChildElementXML() {
+            return "<offer-reject id=\"" + Offer.this.getSessionID() +
+                    "\" xmlns=\"http://jabber.org/protocol/workgroup" + "\"/>";
+        }
+    }
+
+    /**
+     * Packet for accepting an offer.
+     */
+    private class AcceptPacket extends IQ {
+
+        AcceptPacket(String workgroup) {
+            this.setTo(workgroup);
+            this.setType(IQ.Type.SET);
+        }
+
+        public String getChildElementXML() {
+            return "<offer-accept id=\"" + Offer.this.getSessionID() +
+                    "\" xmlns=\"http://jabber.org/protocol/workgroup" + "\"/>";
+        }
+    }
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmation.java b/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmation.java
new file mode 100644
index 0000000..f55d588
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmation.java
@@ -0,0 +1,114 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+
+public class OfferConfirmation extends IQ {
+    private String userJID;
+    private long sessionID;
+
+    public String getUserJID() {
+        return userJID;
+    }
+
+    public void setUserJID(String userJID) {
+        this.userJID = userJID;
+    }
+
+    public long getSessionID() {
+        return sessionID;
+    }
+
+    public void setSessionID(long sessionID) {
+        this.sessionID = sessionID;
+    }
+
+
+    public void notifyService(Connection con, String workgroup, String createdRoomName) {
+        NotifyServicePacket packet = new NotifyServicePacket(workgroup, createdRoomName);
+        con.sendPacket(packet);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<offer-confirmation xmlns=\"http://jabber.org/protocol/workgroup\">");
+        buf.append("</offer-confirmation>");
+        return buf.toString();
+    }
+
+    public static class Provider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            final OfferConfirmation confirmation = new OfferConfirmation();
+
+            boolean done = false;
+            while (!done) {
+                parser.next();
+                String elementName = parser.getName();
+                if (parser.getEventType() == XmlPullParser.START_TAG && "user-jid".equals(elementName)) {
+                    try {
+                        confirmation.setUserJID(parser.nextText());
+                    }
+                    catch (NumberFormatException nfe) {
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.START_TAG && "session-id".equals(elementName)) {
+                    try {
+                        confirmation.setSessionID(Long.valueOf(parser.nextText()));
+                    }
+                    catch (NumberFormatException nfe) {
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.END_TAG && "offer-confirmation".equals(elementName)) {
+                    done = true;
+                }
+            }
+
+
+            return confirmation;
+        }
+    }
+
+
+    /**
+     * Packet for notifying server of RoomName
+     */
+    private class NotifyServicePacket extends IQ {
+        String roomName;
+
+        NotifyServicePacket(String workgroup, String roomName) {
+            this.setTo(workgroup);
+            this.setType(IQ.Type.RESULT);
+
+            this.roomName = roomName;
+        }
+
+        public String getChildElementXML() {
+            return "<offer-confirmation  roomname=\"" + roomName + "\" xmlns=\"http://jabber.org/protocol/workgroup" + "\"/>";
+        }
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmationListener.java b/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmationListener.java
new file mode 100644
index 0000000..fb10550
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/OfferConfirmationListener.java
@@ -0,0 +1,32 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.workgroup.agent;
+
+public interface OfferConfirmationListener {
+
+
+    /**
+     * The implementing class instance will be notified via this when the AgentSession has confirmed
+     * the acceptance of the <code>Offer</code>. The instance will then have the ability to create the room and
+     * send the service the room name created for tracking.
+     *
+     * @param confirmedOffer the ConfirmedOffer
+     */
+    void offerConfirmed(OfferConfirmation confirmedOffer);
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/OfferContent.java b/src/org/jivesoftware/smackx/workgroup/agent/OfferContent.java
new file mode 100644
index 0000000..a11ddc3
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/OfferContent.java
@@ -0,0 +1,55 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+/**
+ * Type of content being included in the offer. The content actually explains the reason
+ * the agent is getting an offer.
+ *
+ * @author Gaston Dombiak
+ */
+public abstract class OfferContent {
+
+    /**
+     * Returns true if the content of the offer is related to a user request. This is the
+     * most common type of offers an agent should receive.
+     *
+     * @return true if the content of the offer is related to a user request.
+     */
+    abstract boolean isUserRequest();
+
+    /**
+     * Returns true if the content of the offer is related to a room invitation made by another
+     * agent. This type of offer include the room to join, metadata sent by the user while joining
+     * the queue and the reason why the agent is being invited.
+     *
+     * @return true if the content of the offer is related to a room invitation made by another agent.
+     */
+    abstract boolean isInvitation();
+
+    /**
+     * Returns true if the content of the offer is related to a service transfer made by another
+     * agent. This type of offers include the room to join, metadata sent by the user while joining the
+     * queue and the reason why the agent is receiving the transfer offer.
+     *
+     * @return true if the content of the offer is related to a service transfer made by another agent.
+     */
+    abstract boolean isTransfer();
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/OfferListener.java b/src/org/jivesoftware/smackx/workgroup/agent/OfferListener.java
new file mode 100644
index 0000000..5efde99
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/OfferListener.java
@@ -0,0 +1,49 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+/**
+ * An interface which all classes interested in hearing about chat offers associated to a particular
+ *  AgentSession instance should implement.<br>
+ *
+ * @author Matt Tucker
+ * @author loki der quaeler
+ * @see org.jivesoftware.smackx.workgroup.agent.AgentSession
+ */
+public interface OfferListener {
+
+    /**
+     * The implementing class instance will be notified via this when the AgentSession has received
+     *  an offer for a chat. The instance will then have the ability to accept, reject, or ignore
+     *  the request (resulting in a revocation-by-timeout).
+     *
+     * @param request the Offer instance embodying the details of the offer
+     */
+    public void offerReceived (Offer request);
+
+    /**
+     * The implementing class instance will be notified via this when the AgentSessino has received
+     *  a revocation of a previously extended offer.
+     *
+     * @param revokedOffer the RevokedOffer instance embodying the details of the revoked offer
+     */
+    public void offerRevoked (RevokedOffer revokedOffer);
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/QueueUsersListener.java b/src/org/jivesoftware/smackx/workgroup/agent/QueueUsersListener.java
new file mode 100644
index 0000000..9fcff9a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/QueueUsersListener.java
@@ -0,0 +1,60 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import java.util.Date;
+import java.util.Set;
+
+import org.jivesoftware.smackx.workgroup.QueueUser;
+
+public interface QueueUsersListener {
+
+    /**
+     * The status of the queue was updated.
+     *
+     * @param queue the workgroup queue.
+     * @param status the status of queue.
+     */
+    public void statusUpdated(WorkgroupQueue queue, WorkgroupQueue.Status status);
+
+    /**
+     * The average wait time of the queue was updated.
+     *
+     * @param queue the workgroup queue.
+     * @param averageWaitTime the average wait time of the queue.
+     */
+    public void averageWaitTimeUpdated(WorkgroupQueue queue, int averageWaitTime);
+
+    /**
+     * The date of oldest entry waiting in the queue was updated.
+     *
+     * @param queue the workgroup queue.
+     * @param oldestEntry the date of the oldest entry waiting in the queue.
+     */
+    public void oldestEntryUpdated(WorkgroupQueue queue, Date oldestEntry);
+
+    /**
+     * The list of users waiting in the queue was updated.
+     *
+     * @param queue the workgroup queue.
+     * @param users the list of users waiting in the queue.
+     */
+    public void usersUpdated(WorkgroupQueue queue, Set<QueueUser> users);
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/RevokedOffer.java b/src/org/jivesoftware/smackx/workgroup/agent/RevokedOffer.java
new file mode 100644
index 0000000..dab4d91
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/RevokedOffer.java
@@ -0,0 +1,98 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import java.util.Date;
+
+/**
+ * An immutable simple class to embody the information concerning a revoked offer, this is namely
+ *  the reason, the workgroup, the userJID, and the timestamp which the message was received.<br>
+ *
+ * @author loki der quaeler
+ */
+public class RevokedOffer {
+
+    private String userJID;
+    private String userID;
+    private String workgroupName;
+    private String sessionID;
+    private String reason;
+    private Date timestamp;
+
+    /**
+     *
+     * @param userJID the JID of the user for which this revocation was issued.
+     * @param userID the user ID of the user for which this revocation was issued.
+     * @param workgroupName the fully qualified name of the workgroup
+     * @param sessionID the session id attributed to this chain of packets
+     * @param reason the server issued message as to why this revocation was issued.
+     * @param timestamp the timestamp at which the revocation was issued
+     */
+    RevokedOffer(String userJID, String userID, String workgroupName, String sessionID,
+            String reason, Date timestamp) {
+        super();
+
+        this.userJID = userJID;
+        this.userID = userID;
+        this.workgroupName = workgroupName;
+        this.sessionID = sessionID;
+        this.reason = reason;
+        this.timestamp = timestamp;
+    }
+
+    public String getUserJID() {
+        return userJID;
+    }
+
+    /**
+     * @return the jid of the user for which this revocation was issued
+     */
+    public String getUserID() {
+        return this.userID;
+    }
+
+    /**
+     * @return the fully qualified name of the workgroup
+     */
+    public String getWorkgroupName() {
+        return this.workgroupName;
+    }
+
+    /**
+     * @return the session id which will associate all packets for the pending chat
+     */
+    public String getSessionID() {
+        return this.sessionID;
+    }
+
+    /**
+     * @return the server issued message as to why this revocation was issued
+     */
+    public String getReason() {
+        return this.reason;
+    }
+
+    /**
+     * @return the timestamp at which the revocation was issued
+     */
+    public Date getTimestamp() {
+        return this.timestamp;
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java b/src/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java
new file mode 100644
index 0000000..8a3801f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/TranscriptManager.java
@@ -0,0 +1,100 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smackx.workgroup.packet.Transcript;
+import org.jivesoftware.smackx.workgroup.packet.Transcripts;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+
+/**
+ * A TranscriptManager helps to retrieve the full conversation transcript of a given session
+ * {@link #getTranscript(String, String)} or to retrieve a list with the summary of all the
+ * conversations that a user had {@link #getTranscripts(String, String)}.
+ *
+ * @author Gaston Dombiak
+ */
+public class TranscriptManager {
+    private Connection connection;
+
+    public TranscriptManager(Connection connection) {
+        this.connection = connection;
+    }
+
+    /**
+     * Returns the full conversation transcript of a given session.
+     *
+     * @param sessionID the id of the session to get the full transcript.
+     * @param workgroupJID the JID of the workgroup that will process the request.
+     * @return the full conversation transcript of a given session.
+     * @throws XMPPException if an error occurs while getting the information.
+     */
+    public Transcript getTranscript(String workgroupJID, String sessionID) throws XMPPException {
+        Transcript request = new Transcript(sessionID);
+        request.setTo(workgroupJID);
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        // Send the request
+        connection.sendPacket(request);
+
+        Transcript response = (Transcript) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Returns the transcripts of a given user. The answer will contain the complete history of
+     * conversations that a user had.
+     *
+     * @param userID the id of the user to get his conversations.
+     * @param workgroupJID the JID of the workgroup that will process the request.
+     * @return the transcripts of a given user.
+     * @throws XMPPException if an error occurs while getting the information.
+     */
+    public Transcripts getTranscripts(String workgroupJID, String userID) throws XMPPException {
+        Transcripts request = new Transcripts(userID);
+        request.setTo(workgroupJID);
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        // Send the request
+        connection.sendPacket(request);
+
+        Transcripts response = (Transcripts) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java b/src/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java
new file mode 100644
index 0000000..8260cd6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/TranscriptSearchManager.java
@@ -0,0 +1,111 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import org.jivesoftware.smackx.workgroup.packet.TranscriptSearch;
+import org.jivesoftware.smack.PacketCollector;
+import org.jivesoftware.smack.SmackConfiguration;
+import org.jivesoftware.smack.Connection;
+import org.jivesoftware.smack.XMPPException;
+import org.jivesoftware.smack.filter.PacketIDFilter;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.ReportedData;
+
+/**
+ * A TranscriptSearchManager helps to retrieve the form to use for searching transcripts
+ * {@link #getSearchForm(String)} or to submit a search form and return the results of
+ * the search {@link #submitSearch(String, Form)}.
+ *
+ * @author Gaston Dombiak
+ */
+public class TranscriptSearchManager {
+    private Connection connection;
+
+    public TranscriptSearchManager(Connection connection) {
+        this.connection = connection;
+    }
+
+    /**
+     * Returns the Form to use for searching transcripts. It is unlikely that the server
+     * will change the form (without a restart) so it is safe to keep the returned form
+     * for future submissions.
+     *
+     * @param serviceJID the address of the workgroup service.
+     * @return the Form to use for searching transcripts.
+     * @throws XMPPException if an error occurs while sending the request to the server.
+     */
+    public Form getSearchForm(String serviceJID) throws XMPPException {
+        TranscriptSearch search = new TranscriptSearch();
+        search.setType(IQ.Type.GET);
+        search.setTo(serviceJID);
+
+        PacketCollector collector = connection.createPacketCollector(
+                new PacketIDFilter(search.getPacketID()));
+        connection.sendPacket(search);
+
+        TranscriptSearch response = (TranscriptSearch) collector.nextResult(
+                SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return Form.getFormFrom(response);
+    }
+
+    /**
+     * Submits the completed form and returns the result of the transcript search. The result
+     * will include all the data returned from the server so be careful with the amount of
+     * data that the search may return.
+     *
+     * @param serviceJID    the address of the workgroup service.
+     * @param completedForm the filled out search form.
+     * @return the result of the transcript search.
+     * @throws XMPPException if an error occurs while submiting the search to the server.
+     */
+    public ReportedData submitSearch(String serviceJID, Form completedForm) throws XMPPException {
+        TranscriptSearch search = new TranscriptSearch();
+        search.setType(IQ.Type.GET);
+        search.setTo(serviceJID);
+        search.addExtension(completedForm.getDataFormToSend());
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(search.getPacketID()));
+        connection.sendPacket(search);
+
+        TranscriptSearch response = (TranscriptSearch) collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return ReportedData.getReportedDataFrom(response);
+    }
+}
+
+
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/TransferRequest.java b/src/org/jivesoftware/smackx/workgroup/agent/TransferRequest.java
new file mode 100644
index 0000000..a3abbaa
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/TransferRequest.java
@@ -0,0 +1,62 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+/**
+ * Request sent by an agent to transfer a support session to another agent or user.
+ *
+ * @author Gaston Dombiak
+ */
+public class TransferRequest extends OfferContent {
+
+    private String inviter;
+    private String room;
+    private String reason;
+
+    public TransferRequest(String inviter, String room, String reason) {
+        this.inviter = inviter;
+        this.room = room;
+        this.reason = reason;
+    }
+
+    public String getInviter() {
+        return inviter;
+    }
+
+    public String getRoom() {
+        return room;
+    }
+
+    public String getReason() {
+        return reason;
+    }
+
+    boolean isUserRequest() {
+        return false;
+    }
+
+    boolean isInvitation() {
+        return false;
+    }
+
+    boolean isTransfer() {
+        return true;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/UserRequest.java b/src/org/jivesoftware/smackx/workgroup/agent/UserRequest.java
new file mode 100644
index 0000000..ccaaaf3
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/UserRequest.java
@@ -0,0 +1,47 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+/**
+ * Requests made by users to get support by some agent.
+ *
+ * @author Gaston Dombiak
+ */
+public class UserRequest extends OfferContent {
+    // TODO Do we want to use a singleton? Should we store the userID here?
+    private static UserRequest instance = new UserRequest();
+
+    public static OfferContent getInstance() {
+        return instance;
+    }
+
+    boolean isUserRequest() {
+        return true;
+    }
+
+    boolean isInvitation() {
+        return false;
+    }
+
+    boolean isTransfer() {
+        return false;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/agent/WorkgroupQueue.java b/src/org/jivesoftware/smackx/workgroup/agent/WorkgroupQueue.java
new file mode 100644
index 0000000..b43c826
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/agent/WorkgroupQueue.java
@@ -0,0 +1,224 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.agent;
+
+import java.util.*;
+
+import org.jivesoftware.smackx.workgroup.QueueUser;
+
+/**
+ * A queue in a workgroup, which is a pool of agents that are routed  a specific type of
+ * chat request.
+ */
+public class WorkgroupQueue {
+
+    private String name;
+    private Status status = Status.CLOSED;
+
+    private int averageWaitTime = -1;
+    private Date oldestEntry = null;
+    private Set<QueueUser> users = Collections.emptySet();
+
+    private int maxChats = 0;
+    private int currentChats = 0;
+
+    /**
+     * Creates a new workgroup queue instance.
+     *
+     * @param name the name of the queue.
+     */
+    WorkgroupQueue(String name) {
+        this.name = name;
+    }
+
+    /**
+     * Returns the name of the queue.
+     *
+     * @return the name of the queue.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Returns the status of the queue.
+     *
+     * @return the status of the queue.
+     */
+    public Status getStatus() {
+        return status;
+    }
+
+    void setStatus(Status status) {
+        this.status = status;
+    }
+
+    /**
+     * Returns the number of users waiting in the queue waiting to be routed to
+     * an agent.
+     *
+     * @return the number of users waiting in the queue.
+     */
+    public int getUserCount() {
+        if (users == null) {
+            return 0;
+        }
+        return users.size();
+    }
+
+    /**
+     * Returns an Iterator for the users in the queue waiting to be routed to
+     * an agent (QueueUser instances).
+     *
+     * @return an Iterator for the users waiting in the queue.
+     */
+    public Iterator<QueueUser> getUsers() {
+        if (users == null) {
+            return new HashSet<QueueUser>().iterator();
+        }
+        return Collections.unmodifiableSet(users).iterator();
+    }
+
+    void setUsers(Set<QueueUser> users) {
+        this.users = users;
+    }
+
+    /**
+     * Returns the average amount of time users wait in the queue before being
+     * routed to an agent. If average wait time info isn't available, -1 will
+     * be returned.
+     *
+     * @return the average wait time
+     */
+    public int getAverageWaitTime() {
+        return averageWaitTime;
+    }
+
+    void setAverageWaitTime(int averageTime) {
+        this.averageWaitTime = averageTime;
+    }
+
+    /**
+     * Returns the date of the oldest request waiting in the queue. If there
+     * are no requests waiting to be routed, this method will return <tt>null</tt>.
+     *
+     * @return the date of the oldest request in the queue.
+     */
+    public Date getOldestEntry() {
+        return oldestEntry;
+    }
+
+    void setOldestEntry(Date oldestEntry) {
+        this.oldestEntry = oldestEntry;
+    }
+
+    /**
+     * Returns the maximum number of simultaneous chats the queue can handle.
+     *
+     * @return the max number of chats the queue can handle.
+     */
+    public int getMaxChats() {
+        return maxChats;
+    }
+
+    void setMaxChats(int maxChats) {
+        this.maxChats = maxChats;
+    }
+
+    /**
+     * Returns the current number of active chat sessions in the queue.
+     *
+     * @return the current number of active chat sessions in the queue.
+     */
+    public int getCurrentChats() {
+        return currentChats;
+    }
+
+    void setCurrentChats(int currentChats) {
+        this.currentChats = currentChats;
+    }
+
+    /**
+     * A class to represent the status of the workgroup. The possible values are:
+     *
+     * <ul>
+     *      <li>WorkgroupQueue.Status.OPEN -- the queue is active and accepting new chat requests.
+     *      <li>WorkgroupQueue.Status.ACTIVE -- the queue is active but NOT accepting new chat
+     *          requests.
+     *      <li>WorkgroupQueue.Status.CLOSED -- the queue is NOT active and NOT accepting new
+     *          chat requests.
+     * </ul>
+     */
+    public static class Status {
+
+        /**
+         * The queue is active and accepting new chat requests.
+         */
+        public static final Status OPEN = new Status("open");
+
+        /**
+         * The queue is active but NOT accepting new chat requests. This state might
+         * occur when the workgroup has closed because regular support hours have closed,
+         * but there are still several requests left in the queue.
+         */
+        public static final Status ACTIVE = new Status("active");
+
+        /**
+         * The queue is NOT active and NOT accepting new chat requests.
+         */
+        public static final Status CLOSED = new Status("closed");
+
+        /**
+         * Converts a String into the corresponding status. Valid String values
+         * that can be converted to a status are: "open", "active", and "closed".
+         *
+         * @param type the String value to covert.
+         * @return the corresponding Type.
+         */
+        public static Status fromString(String type) {
+            if (type == null) {
+                return null;
+            }
+            type = type.toLowerCase();
+            if (OPEN.toString().equals(type)) {
+                return OPEN;
+            }
+            else if (ACTIVE.toString().equals(type)) {
+                return ACTIVE;
+            }
+            else if (CLOSED.toString().equals(type)) {
+                return CLOSED;
+            }
+            else {
+                return null;
+            }
+        }
+
+        private String value;
+
+        private Status(String value) {
+            this.value = value;
+        }
+
+        public String toString() {
+            return value;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/forms/WorkgroupForm.java b/src/org/jivesoftware/smackx/workgroup/ext/forms/WorkgroupForm.java
new file mode 100644
index 0000000..f2dc08e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/forms/WorkgroupForm.java
@@ -0,0 +1,82 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.forms;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.xmlpull.v1.XmlPullParser;
+
+public class WorkgroupForm extends IQ {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "workgroup-form";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for WebForm packets.
+     *
+     * @author Derek DeMoro
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public InternalProvider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            WorkgroupForm answer = new WorkgroupForm();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    // Parse the packet extension
+                    answer.addExtension(PacketParserUtils.parsePacketExtension(parser.getName(),
+                            parser.getNamespace(), parser));
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return answer;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatHistory.java b/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatHistory.java
new file mode 100644
index 0000000..7b8d200
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatHistory.java
@@ -0,0 +1,155 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.history;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
+import java.util.List;
+
+/**
+ * IQ provider used to retrieve individual agent information. Each chat session can be mapped
+ * to one or more jids and therefore retrievable.
+ */
+public class AgentChatHistory extends IQ {
+    private String agentJID;
+    private int maxSessions;
+    private long startDate;
+
+    private List<AgentChatSession> agentChatSessions = new ArrayList<AgentChatSession>();
+
+    public AgentChatHistory(String agentJID, int maxSessions, Date startDate) {
+        this.agentJID = agentJID;
+        this.maxSessions = maxSessions;
+        this.startDate = startDate.getTime();
+    }
+
+    public AgentChatHistory(String agentJID, int maxSessions) {
+        this.agentJID = agentJID;
+        this.maxSessions = maxSessions;
+        this.startDate = 0;
+    }
+
+    public AgentChatHistory() {
+    }
+
+    public void addChatSession(AgentChatSession chatSession) {
+        agentChatSessions.add(chatSession);
+    }
+
+    public Collection<AgentChatSession> getAgentChatSessions() {
+        return agentChatSessions;
+    }
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "chat-sessions";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append(" agentJID=\"" + agentJID + "\"");
+        buf.append(" maxSessions=\"" + maxSessions + "\"");
+        buf.append(" startDate=\"" + startDate + "\"");
+
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+    /**
+     * Packet extension provider for AgentHistory packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            AgentChatHistory agentChatHistory = new AgentChatHistory();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("chat-session".equals(parser.getName()))) {
+                    agentChatHistory.addChatSession(parseChatSetting(parser));
+
+                }
+                else if (eventType == XmlPullParser.END_TAG && ELEMENT_NAME.equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return agentChatHistory;
+        }
+
+        private AgentChatSession parseChatSetting(XmlPullParser parser) throws Exception {
+
+            boolean done = false;
+            Date date = null;
+            long duration = 0;
+            String visitorsName = null;
+            String visitorsEmail = null;
+            String sessionID = null;
+            String question = null;
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("date".equals(parser.getName()))) {
+                    String dateStr = parser.nextText();
+                    long l = Long.valueOf(dateStr).longValue();
+                    date = new Date(l);
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("duration".equals(parser.getName()))) {
+                    duration = Long.valueOf(parser.nextText()).longValue();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("visitorsName".equals(parser.getName()))) {
+                    visitorsName = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("visitorsEmail".equals(parser.getName()))) {
+                    visitorsEmail = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("sessionID".equals(parser.getName()))) {
+                    sessionID = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("question".equals(parser.getName()))) {
+                    question = parser.nextText();
+                }
+                else if (eventType == XmlPullParser.END_TAG && "chat-session".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return new AgentChatSession(date, duration, visitorsName, visitorsEmail, sessionID, question);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatSession.java b/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatSession.java
new file mode 100644
index 0000000..5113cda
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/history/AgentChatSession.java
@@ -0,0 +1,93 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.history;
+
+import java.util.Date;
+
+/**
+ * Represents one chat session for an agent.
+ */
+public class AgentChatSession {
+    public Date startDate;
+    public long duration;
+    public String visitorsName;
+    public String visitorsEmail;
+    public String sessionID;
+    public String question;
+
+    public AgentChatSession(Date date, long duration, String visitorsName, String visitorsEmail, String sessionID, String question) {
+        this.startDate = date;
+        this.duration = duration;
+        this.visitorsName = visitorsName;
+        this.visitorsEmail = visitorsEmail;
+        this.sessionID = sessionID;
+        this.question = question;
+    }
+
+    public Date getStartDate() {
+        return startDate;
+    }
+
+    public void setStartDate(Date startDate) {
+        this.startDate = startDate;
+    }
+
+    public long getDuration() {
+        return duration;
+    }
+
+    public void setDuration(long duration) {
+        this.duration = duration;
+    }
+
+    public String getVisitorsName() {
+        return visitorsName;
+    }
+
+    public void setVisitorsName(String visitorsName) {
+        this.visitorsName = visitorsName;
+    }
+
+    public String getVisitorsEmail() {
+        return visitorsEmail;
+    }
+
+    public void setVisitorsEmail(String visitorsEmail) {
+        this.visitorsEmail = visitorsEmail;
+    }
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    public void setQuestion(String question){
+        this.question = question;
+    }
+
+    public String getQuestion(){
+        return question;
+    }
+
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/history/ChatMetadata.java b/src/org/jivesoftware/smackx/workgroup/ext/history/ChatMetadata.java
new file mode 100644
index 0000000..301e1a5
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/history/ChatMetadata.java
@@ -0,0 +1,116 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.history;
+
+import org.jivesoftware.smackx.workgroup.util.MetaDataUtils;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class ChatMetadata extends IQ {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "chat-metadata";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+
+    private String sessionID;
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+
+    private Map<String, List<String>> map = new HashMap<String, List<String>>();
+
+    public void setMetadata(Map<String, List<String>> metadata){
+        this.map = metadata;
+    }
+
+    public Map<String, List<String>> getMetadata(){
+        return map;
+    }
+
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        buf.append("<sessionID>").append(getSessionID()).append("</sessionID>");
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for Metadata packets.
+     *
+     * @author Derek DeMoro
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            final ChatMetadata chatM = new ChatMetadata();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("sessionID")) {
+                       chatM.setSessionID(parser.nextText());
+                    }
+                    else if (parser.getName().equals("metadata")) {
+                        Map<String, List<String>> map = MetaDataUtils.parseMetaData(parser);
+                        chatM.setMetadata(map);
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return chatM;
+        }
+    }
+}
+
+
+
+
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/macros/Macro.java b/src/org/jivesoftware/smackx/workgroup/ext/macros/Macro.java
new file mode 100644
index 0000000..acf6196
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/macros/Macro.java
@@ -0,0 +1,68 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.macros;
+
+/**
+ * Macro datamodel.
+ */
+public class Macro {
+    public static final int TEXT = 0;
+    public static final int URL = 1;
+    public static final int IMAGE = 2;
+
+
+    private String title;
+    private String description;
+    private String response;
+    private int type;
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public void setDescription(String description) {
+        this.description = description;
+    }
+
+    public String getResponse() {
+        return response;
+    }
+
+    public void setResponse(String response) {
+        this.response = response;
+    }
+
+    public int getType() {
+        return type;
+    }
+
+    public void setType(int type) {
+        this.type = type;
+    }
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/macros/MacroGroup.java b/src/org/jivesoftware/smackx/workgroup/ext/macros/MacroGroup.java
new file mode 100644
index 0000000..0742b3d
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/macros/MacroGroup.java
@@ -0,0 +1,143 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.macros;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * MacroGroup datamodel.
+ */
+public class MacroGroup {
+    private List<Macro> macros;
+    private List<MacroGroup> macroGroups;
+
+
+    // Define MacroGroup
+    private String title;
+
+    public MacroGroup() {
+        macros = new ArrayList<Macro>();
+        macroGroups = new ArrayList<MacroGroup>();
+    }
+
+    public void addMacro(Macro macro) {
+        macros.add(macro);
+    }
+
+    public void removeMacro(Macro macro) {
+        macros.remove(macro);
+    }
+
+    public Macro getMacroByTitle(String title) {
+        Collection<Macro> col = Collections.unmodifiableList(macros);
+        Iterator<Macro> iter = col.iterator();
+        while (iter.hasNext()) {
+            Macro macro = (Macro)iter.next();
+            if (macro.getTitle().equalsIgnoreCase(title)) {
+                return macro;
+            }
+        }
+        return null;
+    }
+
+    public void addMacroGroup(MacroGroup group) {
+        macroGroups.add(group);
+    }
+
+    public void removeMacroGroup(MacroGroup group) {
+        macroGroups.remove(group);
+    }
+
+    public Macro getMacro(int location) {
+        return (Macro)macros.get(location);
+    }
+
+    public MacroGroup getMacroGroupByTitle(String title) {
+        Collection<MacroGroup> col = Collections.unmodifiableList(macroGroups);
+        Iterator<MacroGroup> iter = col.iterator();
+        while (iter.hasNext()) {
+            MacroGroup group = (MacroGroup)iter.next();
+            if (group.getTitle().equalsIgnoreCase(title)) {
+                return group;
+            }
+        }
+        return null;
+    }
+
+    public MacroGroup getMacroGroup(int location) {
+        return (MacroGroup)macroGroups.get(location);
+    }
+
+
+    public List<Macro>  getMacros() {
+        return macros;
+    }
+
+    public void setMacros(List<Macro> macros) {
+        this.macros = macros;
+    }
+
+    public List<MacroGroup> getMacroGroups() {
+        return macroGroups;
+    }
+
+    public void setMacroGroups(List<MacroGroup> macroGroups) {
+        this.macroGroups = macroGroups;
+    }
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+    
+    public String toXML() {
+    	StringBuilder buf = new StringBuilder();
+    	buf.append("<macrogroup>");
+    	buf.append("<title>" +  getTitle() + "</title>");
+    	buf.append("<macros>");
+    	for (Macro macro : getMacros())
+		{
+    		buf.append("<macro>");
+    		buf.append("<title>" + macro.getTitle() + "</title>");
+    		buf.append("<type>" + macro.getType() + "</type>");
+    		buf.append("<description>" + macro.getDescription() + "</description>");
+    		buf.append("<response>" + macro.getResponse() + "</response>");
+    		buf.append("</macro>");
+		}
+    	buf.append("</macros>");
+    	
+    	if (getMacroGroups().size() > 0) {
+    		buf.append("<macroGroups>");
+    		for (MacroGroup groups : getMacroGroups()) {
+    			buf.append(groups.toXML());
+    		}
+    		buf.append("</macroGroups>");
+    	}
+    	buf.append("</macrogroup>");
+    	return buf.toString(); 
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/macros/Macros.java b/src/org/jivesoftware/smackx/workgroup/ext/macros/Macros.java
new file mode 100644
index 0000000..869ec57
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/macros/Macros.java
@@ -0,0 +1,198 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.macros;
+
+import java.io.StringReader;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.xmlpull.v1.XmlPullParserFactory;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Macros iq is responsible for handling global and personal macros in the a Live Assistant
+ * Workgroup.
+ */
+public class Macros extends IQ {
+
+    private MacroGroup rootGroup;
+    private boolean personal;
+    private MacroGroup personalMacroGroup;
+
+    public MacroGroup getRootGroup() {
+        return rootGroup;
+    }
+
+    public void setRootGroup(MacroGroup rootGroup) {
+        this.rootGroup = rootGroup;
+    }
+
+    public boolean isPersonal() {
+        return personal;
+    }
+
+    public void setPersonal(boolean personal) {
+        this.personal = personal;
+    }
+
+    public MacroGroup getPersonalMacroGroup() {
+        return personalMacroGroup;
+    }
+
+    public void setPersonalMacroGroup(MacroGroup personalMacroGroup) {
+        this.personalMacroGroup = personalMacroGroup;
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "macros";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        if (isPersonal()) {
+            buf.append("<personal>true</personal>");
+        }
+        if (getPersonalMacroGroup() != null) {        	
+        	buf.append("<personalMacro>");
+        	buf.append(StringUtils.escapeForXML(getPersonalMacroGroup().toXML()));
+        	buf.append("</personalMacro>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for Macro packets.
+     *
+     * @author Derek DeMoro
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public InternalProvider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            Macros macroGroup = new Macros();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("model")) {
+                        String macros = parser.nextText();
+                        MacroGroup group = parseMacroGroups(macros);
+                        macroGroup.setRootGroup(group);
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return macroGroup;
+        }
+        
+        public Macro parseMacro(XmlPullParser parser) throws Exception {
+        	Macro macro = new Macro();
+        	 boolean done = false;
+            while (!done) {
+	        	int eventType = parser.next();
+	        	if (eventType == XmlPullParser.START_TAG) {
+	        		if (parser.getName().equals("title")) {
+	        			parser.next();
+	        			macro.setTitle(parser.getText());
+	        		}
+	        		else if (parser.getName().equals("description")) {
+	        			macro.setDescription(parser.nextText());
+	        		}
+	        		else if (parser.getName().equals("response")) {
+	        			macro.setResponse(parser.nextText());
+	        		}
+	        		else if (parser.getName().equals("type")) {
+	        			macro.setType(Integer.valueOf(parser.nextText()).intValue());
+	        		}
+	        	}
+	            else if (eventType == XmlPullParser.END_TAG) {
+	                if (parser.getName().equals("macro")) {
+	                    done = true;
+	                }
+	            }
+            }
+        	return macro;
+        }
+        
+        public MacroGroup parseMacroGroup(XmlPullParser parser) throws Exception {
+        	MacroGroup group = new MacroGroup();
+        	
+            boolean done = false;
+            while (!done) {
+	        	int eventType = parser.next();
+	        	if (eventType == XmlPullParser.START_TAG) {
+	        		if (parser.getName().equals("macrogroup")) {
+	        			group.addMacroGroup(parseMacroGroup(parser));
+	        		}
+	        		if (parser.getName().equals("title")) {
+	        			group.setTitle(parser.nextText());
+	        		}
+	        		if (parser.getName().equals("macro")) {
+	        			group.addMacro(parseMacro(parser));
+	        		}
+	        	}
+	            else if (eventType == XmlPullParser.END_TAG) {
+	                if (parser.getName().equals("macrogroup")) {
+	                    done = true;
+	                }
+	            }
+            }
+        	return group; 
+        }
+        
+        public MacroGroup parseMacroGroups(String macros) throws Exception {
+
+        	MacroGroup group = null;
+        	XmlPullParser parser = XmlPullParserFactory.newInstance().newPullParser();
+        	parser.setInput(new StringReader(macros));
+			int eventType = parser.getEventType();
+			while (eventType != XmlPullParser.END_DOCUMENT) {		
+				eventType = parser.next();
+				 if (eventType == XmlPullParser.START_TAG) {
+	                    if (parser.getName().equals("macrogroup")) {
+	                    	group = parseMacroGroup(parser);
+	                    }
+				 }
+			}
+			return group;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/ext/notes/ChatNotes.java b/src/org/jivesoftware/smackx/workgroup/ext/notes/ChatNotes.java
new file mode 100644
index 0000000..eff3c6c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/ext/notes/ChatNotes.java
@@ -0,0 +1,155 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.ext.notes;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * IQ packet for retrieving and adding Chat Notes.
+ */
+public class ChatNotes extends IQ {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "chat-notes";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+
+    private String sessionID;
+    private String notes;
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    public String getNotes() {
+        return notes;
+    }
+
+    public void setNotes(String notes) {
+        this.notes = notes;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        buf.append("<sessionID>").append(getSessionID()).append("</sessionID>");
+
+        if (getNotes() != null) {
+            buf.append("<notes>").append(getNotes()).append("</notes>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for ChatNotes packets.
+     *
+     * @author Derek DeMoro
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            ChatNotes chatNotes = new ChatNotes();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("sessionID")) {
+                        chatNotes.setSessionID(parser.nextText());
+                    }
+                    else if (parser.getName().equals("text")) {
+                        String note = parser.nextText();
+                        note = note.replaceAll("\\\\n", "\n");
+                        chatNotes.setNotes(note);
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return chatNotes;
+        }
+    }
+
+    /**
+     * Replaces all instances of oldString with newString in string.
+     *
+     * @param string    the String to search to perform replacements on
+     * @param oldString the String that should be replaced by newString
+     * @param newString the String that will replace all instances of oldString
+     * @return a String will all instances of oldString replaced by newString
+     */
+    public static final String replace(String string, String oldString, String newString) {
+        if (string == null) {
+            return null;
+        }
+        // If the newString is null or zero length, just return the string since there's nothing
+        // to replace.
+        if (newString == null) {
+            return string;
+        }
+        int i = 0;
+        // Make sure that oldString appears at least once before doing any processing.
+        if ((i = string.indexOf(oldString, i)) >= 0) {
+            // Use char []'s, as they are more efficient to deal with.
+            char[] string2 = string.toCharArray();
+            char[] newString2 = newString.toCharArray();
+            int oLength = oldString.length();
+            StringBuilder buf = new StringBuilder(string2.length);
+            buf.append(string2, 0, i).append(newString2);
+            i += oLength;
+            int j = i;
+            // Replace all remaining instances of oldString with newString.
+            while ((i = string.indexOf(oldString, i)) > 0) {
+                buf.append(string2, j, i - j).append(newString2);
+                i += oLength;
+                j = i;
+            }
+            buf.append(string2, j, string2.length - j);
+            return buf.toString();
+        }
+        return string;
+    }
+}
+
+
+
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/AgentInfo.java b/src/org/jivesoftware/smackx/workgroup/packet/AgentInfo.java
new file mode 100644
index 0000000..8b9d230
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/AgentInfo.java
@@ -0,0 +1,132 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * IQ packet for retrieving and changing the Agent personal information.
+ */
+public class AgentInfo extends IQ {
+
+    /**
+    * Element name of the packet extension.
+    */
+   public static final String ELEMENT_NAME = "agent-info";
+
+   /**
+    * Namespace of the packet extension.
+    */
+   public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    private String jid;
+    private String name;
+
+    /**
+     * Returns the Agent's jid.
+     *
+     * @return the Agent's jid.
+     */
+    public String getJid() {
+        return jid;
+    }
+
+    /**
+     * Sets the Agent's jid.
+     *
+     * @param jid the jid of the agent.
+     */
+    public void setJid(String jid) {
+        this.jid = jid;
+    }
+
+    /**
+     * Returns the Agent's name. The name of the agent may be different than the user's name.
+     * This property may be shown in the webchat client.
+     *
+     * @return the Agent's name.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Sets the Agent's name. The name of the agent may be different than the user's name.
+     * This property may be shown in the webchat client.
+     *
+     * @param name the new name of the agent.
+     */
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        if (jid != null) {
+            buf.append("<jid>").append(getJid()).append("</jid>");
+        }
+        if (name != null) {
+            buf.append("<name>").append(getName()).append("</name>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for AgentInfo packets.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            AgentInfo answer = new AgentInfo();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("jid")) {
+                        answer.setJid(parser.nextText());
+                    }
+                    else if (parser.getName().equals("name")) {
+                        answer.setName(parser.nextText());
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return answer;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/AgentStatus.java b/src/org/jivesoftware/smackx/workgroup/packet/AgentStatus.java
new file mode 100644
index 0000000..9f49033
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/AgentStatus.java
@@ -0,0 +1,266 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.*;
+
+/**
+ * Agent status packet.
+ *
+ * @author Matt Tucker
+ */
+public class AgentStatus implements PacketExtension {
+
+    private static final SimpleDateFormat UTC_FORMAT = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+
+    static {
+        UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("GMT+0"));
+    }
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "agent-status";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private String workgroupJID;
+    private List<ChatInfo> currentChats = new ArrayList<ChatInfo>();
+    private int maxChats = -1;
+
+    AgentStatus() {
+    }
+
+    public String getWorkgroupJID() {
+        return workgroupJID;
+    }
+
+    /**
+     * Returns a collection of ChatInfo where each ChatInfo represents a Chat where this agent
+     * is participating.
+     *
+     * @return a collection of ChatInfo where each ChatInfo represents a Chat where this agent
+     *         is participating.
+     */
+    public List<ChatInfo> getCurrentChats() {
+        return Collections.unmodifiableList(currentChats);
+    }
+
+    public int getMaxChats() {
+        return maxChats;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\"");
+        if (workgroupJID != null) {
+            buf.append(" jid=\"").append(workgroupJID).append("\"");
+        }
+        buf.append(">");
+        if (maxChats != -1) {
+            buf.append("<max-chats>").append(maxChats).append("</max-chats>");
+        }
+        if (!currentChats.isEmpty()) {
+            buf.append("<current-chats xmlns= \"http://jivesoftware.com/protocol/workgroup\">");
+            for (Iterator<ChatInfo> it = currentChats.iterator(); it.hasNext();) {
+                buf.append(((ChatInfo)it.next()).toXML());
+            }
+            buf.append("</current-chats>");
+        }
+        buf.append("</").append(this.getElementName()).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * Represents information about a Chat where this Agent is participating.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class ChatInfo {
+
+        private String sessionID;
+        private String userID;
+        private Date date;
+        private String email;
+        private String username;
+        private String question;
+
+        public ChatInfo(String sessionID, String userID, Date date, String email, String username, String question) {
+            this.sessionID = sessionID;
+            this.userID = userID;
+            this.date = date;
+            this.email = email;
+            this.username = username;
+            this.question = question;
+        }
+
+        /**
+         * Returns the sessionID associated to this chat. Each chat will have a unique sessionID
+         * that could be used for retrieving the whole transcript of the conversation.
+         *
+         * @return the sessionID associated to this chat.
+         */
+        public String getSessionID() {
+            return sessionID;
+        }
+
+        /**
+         * Returns the user unique identification of the user that made the initial request and
+         * for which this chat was generated. If the user joined using an anonymous connection
+         * then the userID will be the value of the ID attribute of the USER element. Otherwise,
+         * the userID will be the bare JID of the user that made the request.
+         *
+         * @return the user unique identification of the user that made the initial request.
+         */
+        public String getUserID() {
+            return userID;
+        }
+
+        /**
+         * Returns the date when this agent joined the chat.
+         *
+         * @return the date when this agent joined the chat.
+         */
+        public Date getDate() {
+            return date;
+        }
+
+        /**
+         * Returns the email address associated with the user.
+         *
+         * @return the email address associated with the user.
+         */
+        public String getEmail() {
+            return email;
+        }
+
+        /**
+         * Returns the username(nickname) associated with the user.
+         *
+         * @return the username associated with the user.
+         */
+        public String getUsername() {
+            return username;
+        }
+
+        /**
+         * Returns the question the user asked.
+         *
+         * @return the question the user asked, if any.
+         */
+        public String getQuestion() {
+            return question;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<chat ");
+            if (sessionID != null) {
+                buf.append(" sessionID=\"").append(sessionID).append("\"");
+            }
+            if (userID != null) {
+                buf.append(" userID=\"").append(userID).append("\"");
+            }
+            if (date != null) {
+                buf.append(" startTime=\"").append(UTC_FORMAT.format(date)).append("\"");
+            }
+            if (email != null) {
+                buf.append(" email=\"").append(email).append("\"");
+            }
+            if (username != null) {
+                buf.append(" username=\"").append(username).append("\"");
+            }
+            if (question != null) {
+                buf.append(" question=\"").append(question).append("\"");
+            }
+            buf.append("/>");
+
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Packet extension provider for AgentStatus packets.
+     */
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            AgentStatus agentStatus = new AgentStatus();
+
+            agentStatus.workgroupJID = parser.getAttributeValue("", "jid");
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+
+                if (eventType == XmlPullParser.START_TAG) {
+                    if ("chat".equals(parser.getName())) {
+                        agentStatus.currentChats.add(parseChatInfo(parser));
+                    }
+                    else if ("max-chats".equals(parser.getName())) {
+                        agentStatus.maxChats = Integer.parseInt(parser.nextText());
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG &&
+                    ELEMENT_NAME.equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return agentStatus;
+        }
+
+        private ChatInfo parseChatInfo(XmlPullParser parser) {
+
+            String sessionID = parser.getAttributeValue("", "sessionID");
+            String userID = parser.getAttributeValue("", "userID");
+            Date date = null;
+            try {
+                date = UTC_FORMAT.parse(parser.getAttributeValue("", "startTime"));
+            }
+            catch (ParseException e) {
+            }
+
+            String email = parser.getAttributeValue("", "email");
+            String username = parser.getAttributeValue("", "username");
+            String question = parser.getAttributeValue("", "question");
+
+            return new ChatInfo(sessionID, userID, date, email, username, question);
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/AgentStatusRequest.java b/src/org/jivesoftware/smackx/workgroup/packet/AgentStatusRequest.java
new file mode 100644
index 0000000..48549d2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/AgentStatusRequest.java
@@ -0,0 +1,163 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Set;
+
+/**
+ * Agent status request packet. This packet is used by agents to request the list of
+ * agents in a workgroup. The response packet contains a list of packets. Presence
+ * packets from individual agents follow.
+ *
+ * @author Matt Tucker
+ */
+public class AgentStatusRequest extends IQ {
+
+     /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "agent-status-request";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private Set<Item> agents;
+
+    public AgentStatusRequest() {
+        agents = new HashSet<Item>();
+    }
+
+    public int getAgentCount() {
+        return agents.size();
+    }
+
+    public Set<Item> getAgents() {
+        return Collections.unmodifiableSet(agents);
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        synchronized (agents) {
+            for (Iterator<Item> i=agents.iterator(); i.hasNext(); ) {
+                Item item = (Item) i.next();
+                buf.append("<agent jid=\"").append(item.getJID()).append("\">");
+                if (item.getName() != null) {
+                    buf.append("<name xmlns=\""+ AgentInfo.NAMESPACE + "\">");
+                    buf.append(item.getName());
+                    buf.append("</name>");
+                }
+                buf.append("</agent>");
+            }
+        }
+        buf.append("</").append(this.getElementName()).append("> ");
+        return buf.toString();
+    }
+
+    public static class Item {
+
+        private String jid;
+        private String type;
+        private String name;
+
+        public Item(String jid, String type, String name) {
+            this.jid = jid;
+            this.type = type;
+            this.name = name;
+        }
+
+        public String getJID() {
+            return jid;
+        }
+
+        public String getType() {
+            return type;
+        }
+
+        public String getName() {
+            return name;
+        }
+    }
+
+    /**
+     * Packet extension provider for AgentStatusRequest packets.
+     */
+    public static class Provider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            AgentStatusRequest statusRequest = new AgentStatusRequest();
+
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("agent".equals(parser.getName()))) {
+                    statusRequest.agents.add(parseAgent(parser));
+                }
+                else if (eventType == XmlPullParser.END_TAG &&
+                        "agent-status-request".equals(parser.getName()))
+                {
+                    done = true;
+                }
+            }
+            return statusRequest;
+        }
+
+        private Item parseAgent(XmlPullParser parser) throws Exception {
+
+            boolean done = false;
+            String jid = parser.getAttributeValue("", "jid");
+            String type = parser.getAttributeValue("", "type");
+            String name = null;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("name".equals(parser.getName()))) {
+                    name = parser.nextText();
+                }
+                else if (eventType == XmlPullParser.END_TAG &&
+                        "agent".equals(parser.getName()))
+                {
+                    done = true;
+                }
+            }
+            return new Item(jid, type, name);
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/AgentWorkgroups.java b/src/org/jivesoftware/smackx/workgroup/packet/AgentWorkgroups.java
new file mode 100644
index 0000000..292a640
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/AgentWorkgroups.java
@@ -0,0 +1,129 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents a request for getting the jid of the workgroups where an agent can work or could
+ * represent the result of such request which will contain the list of workgroups JIDs where the
+ * agent can work.
+ *
+ * @author Gaston Dombiak
+ */
+public class AgentWorkgroups extends IQ {
+
+    private String agentJID;
+    private List<String> workgroups;
+
+    /**
+     * Creates an AgentWorkgroups request for the given agent. This IQ will be sent and an answer
+     * will be received with the jid of the workgroups where the agent can work.
+     *
+     * @param agentJID the id of the agent to get his workgroups.
+     */
+    public AgentWorkgroups(String agentJID) {
+        this.agentJID = agentJID;
+        this.workgroups = new ArrayList<String>();
+    }
+
+    /**
+     * Creates an AgentWorkgroups which will contain the JIDs of the workgroups where an agent can
+     * work.
+     *
+     * @param agentJID the id of the agent that can work in the list of workgroups.
+     * @param workgroups the list of workgroup JIDs where the agent can work.
+     */
+    public AgentWorkgroups(String agentJID, List<String> workgroups) {
+        this.agentJID = agentJID;
+        this.workgroups = workgroups;
+    }
+
+    public String getAgentJID() {
+        return agentJID;
+    }
+
+    /**
+     * Returns a list of workgroup JIDs where the agent can work.
+     *
+     * @return a list of workgroup JIDs where the agent can work.
+     */
+    public List<String> getWorkgroups() {
+        return Collections.unmodifiableList(workgroups);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<workgroups xmlns=\"http://jabber.org/protocol/workgroup\" jid=\"")
+                .append(agentJID)
+                .append("\">");
+
+        for (Iterator<String> it=workgroups.iterator(); it.hasNext();) {
+            String workgroupJID = it.next();
+            buf.append("<workgroup jid=\"" + workgroupJID + "\"/>");
+        }
+
+        buf.append("</workgroups>");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for AgentWorkgroups packets.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            String agentJID = parser.getAttributeValue("", "jid");
+            List<String> workgroups = new ArrayList<String>();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    if (parser.getName().equals("workgroup")) {
+                        workgroups.add(parser.getAttributeValue("", "jid"));
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals("workgroups")) {
+                        done = true;
+                    }
+                }
+            }
+
+            return new AgentWorkgroups(agentJID, workgroups);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/DepartQueuePacket.java b/src/org/jivesoftware/smackx/workgroup/packet/DepartQueuePacket.java
new file mode 100644
index 0000000..620291c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/DepartQueuePacket.java
@@ -0,0 +1,75 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+/**
+ * A IQ packet used to depart a workgroup queue. There are two cases for issuing a depart
+ * queue request:<ul>
+ *     <li>The user wants to leave the queue. In this case, an instance of this class
+ *         should be created without passing in a user address.
+ *     <li>An administrator or the server removes wants to remove a user from the queue.
+ *         In that case, the address of the user to remove from the queue should be
+ *         used to create an instance of this class.</ul>
+ *
+ * @author loki der quaeler
+ */
+public class DepartQueuePacket extends IQ {
+
+    private String user;
+
+    /**
+     * Creates a depart queue request packet to the specified workgroup.
+     *
+     * @param workgroup the workgroup to depart.
+     */
+    public DepartQueuePacket(String workgroup) {
+        this(workgroup, null);
+    }
+
+    /**
+     * Creates a depart queue request to the specified workgroup and for the
+     * specified user.
+     *
+     * @param workgroup the workgroup to depart.
+     * @param user the user to make depart from the queue.
+     */
+    public DepartQueuePacket(String workgroup, String user) {
+        this.user = user;
+
+        setTo(workgroup);
+        setType(IQ.Type.SET);
+        setFrom(user);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder("<depart-queue xmlns=\"http://jabber.org/protocol/workgroup\"");
+
+        if (this.user != null) {
+            buf.append("><jid>").append(this.user).append("</jid></depart-queue>");
+        }
+        else {
+            buf.append("/>");
+        }
+
+        return buf.toString();
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/MetaDataProvider.java b/src/org/jivesoftware/smackx/workgroup/packet/MetaDataProvider.java
new file mode 100644
index 0000000..af76986
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/MetaDataProvider.java
@@ -0,0 +1,49 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import java.util.List;
+import java.util.Map;
+
+import org.jivesoftware.smackx.workgroup.MetaData;
+import org.jivesoftware.smackx.workgroup.util.MetaDataUtils;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * This provider parses meta data if it's not contained already in a larger extension provider.
+ *
+ * @author loki der quaeler
+ */
+public class MetaDataProvider implements PacketExtensionProvider {
+
+    /**
+     * PacketExtensionProvider implementation
+     */
+    public PacketExtension parseExtension (XmlPullParser parser)
+        throws Exception {
+        Map<String, List<String>> metaData = MetaDataUtils.parseMetaData(parser);
+
+        return new MetaData(metaData);
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/MonitorPacket.java b/src/org/jivesoftware/smackx/workgroup/packet/MonitorPacket.java
new file mode 100644
index 0000000..0ceecae
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/MonitorPacket.java
@@ -0,0 +1,113 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class MonitorPacket extends IQ {
+
+    private String sessionID;
+
+    private boolean isMonitor;
+
+    public boolean isMonitor() {
+        return isMonitor;
+    }
+
+    public void setMonitor(boolean monitor) {
+        isMonitor = monitor;
+    }
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public void setSessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "monitor";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append(">");
+        if (sessionID != null) {
+            buf.append("<makeOwner sessionID=\""+sessionID+"\"></makeOwner>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+
+    /**
+     * Packet extension provider for Monitor Packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            MonitorPacket packet = new MonitorPacket();
+
+            boolean done = false;
+
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("isMonitor".equals(parser.getName()))) {
+                    String value = parser.nextText();
+                    if ("false".equalsIgnoreCase(value)) {
+                        packet.setMonitor(false);
+                    }
+                    else {
+                        packet.setMonitor(true);
+                    }
+                }
+                else if (eventType == XmlPullParser.END_TAG && "monitor".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            return packet;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/OccupantsInfo.java b/src/org/jivesoftware/smackx/workgroup/packet/OccupantsInfo.java
new file mode 100644
index 0000000..0f80866
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/OccupantsInfo.java
@@ -0,0 +1,173 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.text.SimpleDateFormat;
+import java.util.*;
+
+/**
+ * Packet used for requesting information about occupants of a room or for retrieving information
+ * such information.
+ *
+ * @author Gaston Dombiak
+ */
+public class OccupantsInfo extends IQ {
+
+    private static final SimpleDateFormat UTC_FORMAT = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+
+    static {
+        UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("GMT+0"));
+    }
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "occupants-info";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    private String roomID;
+    private final Set<OccupantInfo> occupants;
+
+    public OccupantsInfo(String roomID) {
+        this.roomID = roomID;
+        this.occupants = new HashSet<OccupantInfo>();
+    }
+
+    public String getRoomID() {
+        return roomID;
+    }
+
+    public int getOccupantsCount() {
+        return occupants.size();
+    }
+
+    public Set<OccupantInfo> getOccupants() {
+        return Collections.unmodifiableSet(occupants);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE);
+        buf.append("\" roomID=\"").append(roomID).append("\">");
+        synchronized (occupants) {
+            for (OccupantInfo occupant : occupants) {
+                buf.append("<occupant>");
+                // Add the occupant jid
+                buf.append("<jid>");
+                buf.append(occupant.getJID());
+                buf.append("</jid>");
+                // Add the occupant nickname
+                buf.append("<name>");
+                buf.append(occupant.getNickname());
+                buf.append("</name>");
+                // Add the date when the occupant joined the room
+                buf.append("<joined>");
+                buf.append(UTC_FORMAT.format(occupant.getJoined()));
+                buf.append("</joined>");
+                buf.append("</occupant>");
+            }
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+    public static class OccupantInfo {
+
+        private String jid;
+        private String nickname;
+        private Date joined;
+
+        public OccupantInfo(String jid, String nickname, Date joined) {
+            this.jid = jid;
+            this.nickname = nickname;
+            this.joined = joined;
+        }
+
+        public String getJID() {
+            return jid;
+        }
+
+        public String getNickname() {
+            return nickname;
+        }
+
+        public Date getJoined() {
+            return joined;
+        }
+    }
+
+    /**
+     * Packet extension provider for AgentStatusRequest packets.
+     */
+    public static class Provider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+            OccupantsInfo occupantsInfo = new OccupantsInfo(parser.getAttributeValue("", "roomID"));
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) &&
+                        ("occupant".equals(parser.getName()))) {
+                    occupantsInfo.occupants.add(parseOccupantInfo(parser));
+                } else if (eventType == XmlPullParser.END_TAG &&
+                        ELEMENT_NAME.equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return occupantsInfo;
+        }
+
+        private OccupantInfo parseOccupantInfo(XmlPullParser parser) throws Exception {
+
+            boolean done = false;
+            String jid = null;
+            String nickname = null;
+            Date joined = null;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("jid".equals(parser.getName()))) {
+                    jid = parser.nextText();
+                } else if ((eventType == XmlPullParser.START_TAG) &&
+                        ("nickname".equals(parser.getName()))) {
+                    nickname = parser.nextText();
+                } else if ((eventType == XmlPullParser.START_TAG) &&
+                        ("joined".equals(parser.getName()))) {
+                    joined = UTC_FORMAT.parse(parser.nextText());
+                } else if (eventType == XmlPullParser.END_TAG &&
+                        "occupant".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return new OccupantInfo(jid, nickname, joined);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/OfferRequestProvider.java b/src/org/jivesoftware/smackx/workgroup/packet/OfferRequestProvider.java
new file mode 100644
index 0000000..8f56b78
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/OfferRequestProvider.java
@@ -0,0 +1,211 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smackx.workgroup.MetaData;
+import org.jivesoftware.smackx.workgroup.agent.InvitationRequest;
+import org.jivesoftware.smackx.workgroup.agent.OfferContent;
+import org.jivesoftware.smackx.workgroup.agent.TransferRequest;
+import org.jivesoftware.smackx.workgroup.agent.UserRequest;
+import org.jivesoftware.smackx.workgroup.util.MetaDataUtils;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * An IQProvider for agent offer requests.
+ *
+ * @author loki der quaeler
+ */
+public class OfferRequestProvider implements IQProvider {
+
+    public OfferRequestProvider() {
+    }
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        int eventType = parser.getEventType();
+        String sessionID = null;
+        int timeout = -1;
+        OfferContent content = null;
+        boolean done = false;
+        Map<String, List<String>> metaData = new HashMap<String, List<String>>();
+
+        if (eventType != XmlPullParser.START_TAG) {
+            // throw exception
+        }
+
+        String userJID = parser.getAttributeValue("", "jid");
+        // Default userID to the JID.
+        String userID = userJID;
+
+        while (!done) {
+            eventType = parser.next();
+
+            if (eventType == XmlPullParser.START_TAG) {
+                String elemName = parser.getName();
+
+                if ("timeout".equals(elemName)) {
+                    timeout = Integer.parseInt(parser.nextText());
+                }
+                else if (MetaData.ELEMENT_NAME.equals(elemName)) {
+                    metaData = MetaDataUtils.parseMetaData(parser);
+                }
+                else if (SessionID.ELEMENT_NAME.equals(elemName)) {
+                   sessionID = parser.getAttributeValue("", "id");
+                }
+                else if (UserID.ELEMENT_NAME.equals(elemName)) {
+                    userID = parser.getAttributeValue("", "id");
+                }
+                else if ("user-request".equals(elemName)) {
+                    content = UserRequest.getInstance();
+                }
+                else if (RoomInvitation.ELEMENT_NAME.equals(elemName)) {
+                    RoomInvitation invitation = (RoomInvitation) PacketParserUtils
+                            .parsePacketExtension(RoomInvitation.ELEMENT_NAME, RoomInvitation.NAMESPACE, parser);
+                    content = new InvitationRequest(invitation.getInviter(), invitation.getRoom(),
+                            invitation.getReason());
+                }
+                else if (RoomTransfer.ELEMENT_NAME.equals(elemName)) {
+                    RoomTransfer transfer = (RoomTransfer) PacketParserUtils
+                            .parsePacketExtension(RoomTransfer.ELEMENT_NAME, RoomTransfer.NAMESPACE, parser);
+                    content = new TransferRequest(transfer.getInviter(), transfer.getRoom(), transfer.getReason());
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if ("offer".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+        }
+
+        OfferRequestPacket offerRequest =
+                new OfferRequestPacket(userJID, userID, timeout, metaData, sessionID, content);
+        offerRequest.setType(IQ.Type.SET);
+
+        return offerRequest;
+    }
+
+    public static class OfferRequestPacket extends IQ {
+
+        private int timeout;
+        private String userID;
+        private String userJID;
+        private Map<String, List<String>> metaData;
+        private String sessionID;
+        private OfferContent content;
+
+        public OfferRequestPacket(String userJID, String userID, int timeout, Map<String, List<String>> metaData,
+                String sessionID, OfferContent content)
+        {
+            this.userJID = userJID;
+            this.userID = userID;
+            this.timeout = timeout;
+            this.metaData = metaData;
+            this.sessionID = sessionID;
+            this.content = content;
+        }
+
+        /**
+         * Returns the userID, which is either the same as the userJID or a special
+         * value that the user provided as part of their "join queue" request.
+         *
+         * @return the user ID.
+         */
+        public String getUserID() {
+            return userID;
+        }
+
+        /**
+         * The JID of the user that made the "join queue" request.
+         *
+         * @return the user JID.
+         */
+        public String getUserJID() {
+            return userJID;
+        }
+
+        /**
+         * Returns the session ID associated with the request and ensuing chat. If the offer
+         * does not contain a session ID, <tt>null</tt> will be returned.
+         *
+         * @return the session id associated with the request.
+         */
+        public String getSessionID() {
+            return sessionID;
+        }
+
+        /**
+         * Returns the number of seconds the agent has to accept the offer before
+         * it times out.
+         *
+         * @return the offer timeout (in seconds).
+         */
+        public int getTimeout() {
+            return this.timeout;
+        }
+
+        public OfferContent getContent() {
+            return content;
+        }
+
+        /**
+         * Returns any meta-data associated with the offer.
+         *
+         * @return meta-data associated with the offer.
+         */
+        public Map<String, List<String>> getMetaData() {
+            return this.metaData;
+        }
+
+        public String getChildElementXML () {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<offer xmlns=\"http://jabber.org/protocol/workgroup\" jid=\"").append(userJID).append("\">");
+            buf.append("<timeout>").append(timeout).append("</timeout>");
+
+            if (sessionID != null) {
+                buf.append('<').append(SessionID.ELEMENT_NAME);
+                buf.append(" session=\"");
+                buf.append(getSessionID()).append("\" xmlns=\"");
+                buf.append(SessionID.NAMESPACE).append("\"/>");
+            }
+
+            if (metaData != null) {
+                buf.append(MetaDataUtils.serializeMetaData(metaData));
+            }
+
+            if (userID != null) {
+                buf.append('<').append(UserID.ELEMENT_NAME);
+                buf.append(" id=\"");
+                buf.append(userID).append("\" xmlns=\"");
+                buf.append(UserID.NAMESPACE).append("\"/>");
+            }
+
+            buf.append("</offer>");
+
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/OfferRevokeProvider.java b/src/org/jivesoftware/smackx/workgroup/packet/OfferRevokeProvider.java
new file mode 100644
index 0000000..202824c
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/OfferRevokeProvider.java
@@ -0,0 +1,112 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * An IQProvider class which has savvy about the offer-revoke tag.<br>
+ *
+ * @author loki der quaeler
+ */
+public class OfferRevokeProvider implements IQProvider {
+
+    public IQ parseIQ (XmlPullParser parser) throws Exception {
+        // The parser will be positioned on the opening IQ tag, so get the JID attribute.
+        String userJID = parser.getAttributeValue("", "jid");
+        // Default the userID to the JID.
+        String userID = userJID;
+        String reason = null;
+        String sessionID = null;
+        boolean done = false;
+
+        while (!done) {
+            int eventType = parser.next();
+
+            if ((eventType == XmlPullParser.START_TAG) && parser.getName().equals("reason")) {
+                reason = parser.nextText();
+            }
+            else if ((eventType == XmlPullParser.START_TAG)
+                         && parser.getName().equals(SessionID.ELEMENT_NAME)) {
+                sessionID = parser.getAttributeValue("", "id");
+            }
+            else if ((eventType == XmlPullParser.START_TAG)
+                         && parser.getName().equals(UserID.ELEMENT_NAME)) {
+                userID = parser.getAttributeValue("", "id");
+            }
+            else if ((eventType == XmlPullParser.END_TAG) && parser.getName().equals(
+                    "offer-revoke"))
+            {
+                done = true;
+            }
+        }
+
+        return new OfferRevokePacket(userJID, userID, reason, sessionID);
+    }
+
+    public class OfferRevokePacket extends IQ {
+
+        private String userJID;
+        private String userID;
+        private String sessionID;
+        private String reason;
+
+        public OfferRevokePacket (String userJID, String userID, String cause, String sessionID) {
+            this.userJID = userJID;
+            this.userID = userID;
+            this.reason = cause;
+            this.sessionID = sessionID;
+        }
+
+        public String getUserJID() {
+            return userJID;
+        }
+
+        public String getUserID() {
+            return this.userID;
+        }
+
+        public String getReason() {
+            return this.reason;
+        }
+
+        public String getSessionID() {
+            return this.sessionID;
+        }
+
+        public String getChildElementXML () {
+            StringBuilder buf = new StringBuilder();
+            buf.append("<offer-revoke xmlns=\"http://jabber.org/protocol/workgroup\" jid=\"").append(userID).append("\">");
+            if (reason != null) {
+                buf.append("<reason>").append(reason).append("</reason>");
+            }
+            if (sessionID != null) {
+                buf.append(new SessionID(sessionID).toXML());
+            }
+            if (userID != null) {
+                buf.append(new UserID(userID).toXML());
+            }
+            buf.append("</offer-revoke>");
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/QueueDetails.java b/src/org/jivesoftware/smackx/workgroup/packet/QueueDetails.java
new file mode 100644
index 0000000..ef11a78
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/QueueDetails.java
@@ -0,0 +1,199 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smackx.workgroup.QueueUser;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Set;
+
+/**
+ * Queue details packet extension, which contains details about the users
+ * currently in a queue.
+ */
+public class QueueDetails implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "notify-queue-details";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private static final String DATE_FORMAT = "yyyyMMdd'T'HH:mm:ss";
+
+    private SimpleDateFormat dateFormat = new SimpleDateFormat(DATE_FORMAT);
+    /**
+     * The list of users in the queue.
+     */
+    private Set<QueueUser> users;
+
+    /**
+     * Creates a new QueueDetails packet
+     */
+    private QueueDetails() {
+        users = new HashSet<QueueUser>();
+    }
+
+    /**
+     * Returns the number of users currently in the queue that are waiting to
+     * be routed to an agent.
+     *
+     * @return the number of users in the queue.
+     */
+    public int getUserCount() {
+        return users.size();
+    }
+
+    /**
+     * Returns the set of users in the queue that are waiting to
+     * be routed to an agent (as QueueUser objects).
+     *
+     * @return a Set for the users waiting in a queue.
+     */
+    public Set<QueueUser> getUsers() {
+        synchronized (users) {
+            return users;
+        }
+    }
+
+    /**
+     * Adds a user to the packet.
+     *
+     * @param user the user.
+     */
+    private void addUser(QueueUser user) {
+        synchronized (users) {
+            users.add(user);
+        }
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+
+        synchronized (users) {
+            for (Iterator<QueueUser> i=users.iterator(); i.hasNext(); ) {
+                QueueUser user = (QueueUser)i.next();
+                int position = user.getQueuePosition();
+                int timeRemaining = user.getEstimatedRemainingTime();
+                Date timestamp = user.getQueueJoinTimestamp();
+
+                buf.append("<user jid=\"").append(user.getUserID()).append("\">");
+
+                if (position != -1) {
+                    buf.append("<position>").append(position).append("</position>");
+                }
+
+                if (timeRemaining != -1) {
+                    buf.append("<time>").append(timeRemaining).append("</time>");
+                }
+
+                if (timestamp != null) {
+                    buf.append("<join-time>");
+                    buf.append(dateFormat.format(timestamp));
+                    buf.append("</join-time>");
+                }
+
+                buf.append("</user>");
+            }
+        }
+        buf.append("</").append(ELEMENT_NAME).append(">");
+        return buf.toString();
+    }
+
+    /**
+     * Provider class for QueueDetails packet extensions.
+     */
+    public static class Provider implements PacketExtensionProvider {
+        
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            
+            SimpleDateFormat dateFormat = new SimpleDateFormat(DATE_FORMAT);
+            QueueDetails queueDetails = new QueueDetails();
+
+            int eventType = parser.getEventType();
+            while (eventType != XmlPullParser.END_TAG &&
+                    "notify-queue-details".equals(parser.getName()))
+            {
+                eventType = parser.next();
+                while ((eventType == XmlPullParser.START_TAG) && "user".equals(parser.getName())) {
+                    String uid = null;
+                    int position = -1;
+                    int time = -1;
+                    Date joinTime = null;
+
+                    uid = parser.getAttributeValue("", "jid");
+               
+                    if (uid == null) {
+                        // throw exception
+                    }
+
+                    eventType = parser.next();
+                    while ((eventType != XmlPullParser.END_TAG)
+                                || (! "user".equals(parser.getName())))
+                    {                        
+                        if ("position".equals(parser.getName())) {
+                            position = Integer.parseInt(parser.nextText());
+                        }
+                        else if ("time".equals(parser.getName())) {
+                            time = Integer.parseInt(parser.nextText());
+                        }
+                        else if ("join-time".equals(parser.getName())) {
+                            joinTime = dateFormat.parse(parser.nextText());                            
+                        }
+                        else if( parser.getName().equals( "waitTime" ) ) {
+                            Date wait = dateFormat.parse(parser.nextText());
+                            System.out.println( wait );
+                        }
+
+                        eventType = parser.next();
+
+                        if (eventType != XmlPullParser.END_TAG) {
+                            // throw exception
+                        }
+                    }                   
+
+                    queueDetails.addUser(new QueueUser(uid, position, time, joinTime));
+
+                    eventType = parser.next();
+                }
+            }
+            return queueDetails;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/QueueOverview.java b/src/org/jivesoftware/smackx/workgroup/packet/QueueOverview.java
new file mode 100644
index 0000000..a559579
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/QueueOverview.java
@@ -0,0 +1,160 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smackx.workgroup.agent.WorkgroupQueue;
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+public class QueueOverview implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static String ELEMENT_NAME = "notify-queue";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private static final String DATE_FORMAT = "yyyyMMdd'T'HH:mm:ss";
+    private SimpleDateFormat dateFormat = new SimpleDateFormat(DATE_FORMAT);
+
+    private int averageWaitTime;
+    private Date oldestEntry;
+    private int userCount;
+    private WorkgroupQueue.Status status;
+
+    QueueOverview() {
+        this.averageWaitTime = -1;
+        this.oldestEntry = null;
+        this.userCount = -1;
+        this.status = null;
+    }
+
+    void setAverageWaitTime(int averageWaitTime) {
+        this.averageWaitTime = averageWaitTime;
+    }
+
+    public int getAverageWaitTime () {
+        return averageWaitTime;
+    }
+
+    void setOldestEntry(Date oldestEntry) {
+        this.oldestEntry = oldestEntry;
+    }
+
+    public Date getOldestEntry() {
+        return oldestEntry;
+    }
+
+    void setUserCount(int userCount) {
+        this.userCount = userCount;
+    }
+
+    public int getUserCount() {
+        return userCount;
+    }
+
+    public WorkgroupQueue.Status getStatus() {
+        return status;
+    }
+
+    void setStatus(WorkgroupQueue.Status status) {
+        this.status = status;
+    }
+
+    public String getElementName () {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace () {
+        return NAMESPACE;
+    }
+
+    public String toXML () {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+
+        if (userCount != -1) {
+            buf.append("<count>").append(userCount).append("</count>");
+        }
+        if (oldestEntry != null) {
+            buf.append("<oldest>").append(dateFormat.format(oldestEntry)).append("</oldest>");
+        }
+        if (averageWaitTime != -1) {
+            buf.append("<time>").append(averageWaitTime).append("</time>");
+        }
+        if (status != null) {
+            buf.append("<status>").append(status).append("</status>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append(">");
+
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension (XmlPullParser parser) throws Exception {
+            int eventType = parser.getEventType();
+            QueueOverview queueOverview = new QueueOverview();            
+            SimpleDateFormat dateFormat = new SimpleDateFormat(DATE_FORMAT);
+
+            if (eventType != XmlPullParser.START_TAG) {
+                // throw exception
+            }
+
+            eventType = parser.next();
+            while ((eventType != XmlPullParser.END_TAG)
+                         || (!ELEMENT_NAME.equals(parser.getName())))
+            {
+                if ("count".equals(parser.getName())) {
+                    queueOverview.setUserCount(Integer.parseInt(parser.nextText()));
+                }
+                else if ("time".equals(parser.getName())) {
+                    queueOverview.setAverageWaitTime(Integer.parseInt(parser.nextText()));
+                }
+                else if ("oldest".equals(parser.getName())) {
+                    queueOverview.setOldestEntry((dateFormat.parse(parser.nextText())));                    
+                }
+                else if ("status".equals(parser.getName())) {
+                    queueOverview.setStatus(WorkgroupQueue.Status.fromString(parser.nextText()));
+                }
+
+                eventType = parser.next();
+
+                if (eventType != XmlPullParser.END_TAG) {
+                    // throw exception
+                }
+            }
+
+            if (eventType != XmlPullParser.END_TAG) {
+                // throw exception
+            }
+
+            return queueOverview;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/QueueUpdate.java b/src/org/jivesoftware/smackx/workgroup/packet/QueueUpdate.java
new file mode 100644
index 0000000..c326a57
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/QueueUpdate.java
@@ -0,0 +1,122 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * An IQ packet that encapsulates both types of workgroup queue
+ * status notifications -- position updates, and estimated time
+ * left in the queue updates.
+ */
+public class QueueUpdate implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "queue-status";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private int position;
+    private int remainingTime;
+
+    public QueueUpdate(int position, int remainingTime) {
+        this.position = position;
+        this.remainingTime = remainingTime;
+    }
+
+    /**
+     * Returns the user's position in the workgroup queue, or -1 if the
+     * value isn't set on this packet.
+     *
+     * @return the position in the workgroup queue.
+     */
+    public int getPosition() {
+        return this.position;
+    }
+
+    /**
+     * Returns the user's estimated time left in the workgroup queue, or
+     * -1 if the value isn't set on this packet.
+     *
+     * @return the estimated time left in the workgroup queue.
+     */
+    public int getRemaingTime() {
+        return remainingTime;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+        buf.append("<queue-status xmlns=\"http://jabber.org/protocol/workgroup\">");
+        if (position != -1) {
+            buf.append("<position>").append(position).append("</position>");
+        }
+        if (remainingTime != -1) {
+            buf.append("<time>").append(remainingTime).append("</time>");
+        }
+        buf.append("</queue-status>");
+        return buf.toString();
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            boolean done = false;
+            int position = -1;
+            int timeRemaining = -1;
+            while (!done) {
+                parser.next();
+                String elementName = parser.getName();
+                if (parser.getEventType() == XmlPullParser.START_TAG && "position".equals(elementName)) {
+                    try {
+                        position = Integer.parseInt(parser.nextText());
+                    }
+                    catch (NumberFormatException nfe) {
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.START_TAG && "time".equals(elementName)) {
+                    try {
+                        timeRemaining = Integer.parseInt(parser.nextText());
+                    }
+                    catch (NumberFormatException nfe) {
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.END_TAG && "queue-status".equals(elementName)) {
+                    done = true;
+                }
+            }
+            return new QueueUpdate(position, timeRemaining);
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/RoomInvitation.java b/src/org/jivesoftware/smackx/workgroup/packet/RoomInvitation.java
new file mode 100644
index 0000000..34555de
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/RoomInvitation.java
@@ -0,0 +1,177 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Packet extension for {@link org.jivesoftware.smackx.workgroup.agent.InvitationRequest}.
+ *
+ * @author Gaston Dombiak
+ */
+public class RoomInvitation implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "invite";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    /**
+     * Type of entity being invited to a groupchat support session.
+     */
+    private Type type;
+    /**
+     * JID of the entity being invited. The entity could be another agent, user , a queue or a workgroup. In
+     * the case of a queue or a workgroup the server will select the best agent to invite. 
+     */
+    private String invitee;
+    /**
+     * Full JID of the user that sent the invitation.
+     */
+    private String inviter;
+    /**
+     * ID of the session that originated the initial user request.
+     */
+    private String sessionID;
+    /**
+     * JID of the room to join if offer is accepted.
+     */
+    private String room;
+    /**
+     * Text provided by the inviter explaining the reason why the invitee is invited. 
+     */
+    private String reason;
+
+    public RoomInvitation(Type type, String invitee, String sessionID, String reason) {
+        this.type = type;
+        this.invitee = invitee;
+        this.sessionID = sessionID;
+        this.reason = reason;
+    }
+
+    private RoomInvitation() {
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String getInviter() {
+        return inviter;
+    }
+
+    public String getRoom() {
+        return room;
+    }
+
+    public String getReason() {
+        return reason;
+    }
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE);
+        buf.append("\" type=\"").append(type).append("\">");
+        buf.append("<session xmlns=\"http://jivesoftware.com/protocol/workgroup\" id=\"").append(sessionID).append("\"></session>");
+        if (invitee != null) {
+            buf.append("<invitee>").append(invitee).append("</invitee>");
+        }
+        if (inviter != null) {
+            buf.append("<inviter>").append(inviter).append("</inviter>");
+        }
+        if (reason != null) {
+            buf.append("<reason>").append(reason).append("</reason>");
+        }
+        // Add packet extensions, if any are defined.
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * Type of entity being invited to a groupchat support session.
+     */
+    public static enum Type {
+        /**
+         * A user is being invited to a groupchat support session. The user could be another agent
+         * or just a regular XMPP user.
+         */
+        user,
+        /**
+         * Some agent of the specified queue will be invited to the groupchat support session.
+         */
+        queue,
+        /**
+         * Some agent of the specified workgroup will be invited to the groupchat support session.
+         */
+        workgroup
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            final RoomInvitation invitation = new RoomInvitation();
+            invitation.type = Type.valueOf(parser.getAttributeValue("", "type"));
+
+            boolean done = false;
+            while (!done) {
+                parser.next();
+                String elementName = parser.getName();
+                if (parser.getEventType() == XmlPullParser.START_TAG) {
+                    if ("session".equals(elementName)) {
+                        invitation.sessionID = parser.getAttributeValue("", "id");
+                    }
+                    else if ("invitee".equals(elementName)) {
+                        invitation.invitee = parser.nextText();
+                    }
+                    else if ("inviter".equals(elementName)) {
+                        invitation.inviter = parser.nextText();
+                    }
+                    else if ("reason".equals(elementName)) {
+                        invitation.reason = parser.nextText();
+                    }
+                    else if ("room".equals(elementName)) {
+                        invitation.room = parser.nextText();
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.END_TAG && ELEMENT_NAME.equals(elementName)) {
+                    done = true;
+                }
+            }
+            return invitation;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/RoomTransfer.java b/src/org/jivesoftware/smackx/workgroup/packet/RoomTransfer.java
new file mode 100644
index 0000000..d1e83e2
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/RoomTransfer.java
@@ -0,0 +1,177 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * Packet extension for {@link org.jivesoftware.smackx.workgroup.agent.TransferRequest}.
+ *
+ * @author Gaston Dombiak
+ */
+public class RoomTransfer implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "transfer";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    /**
+     * Type of entity being invited to a groupchat support session.
+     */
+    private RoomTransfer.Type type;
+    /**
+     * JID of the entity being invited. The entity could be another agent, user , a queue or a workgroup. In
+     * the case of a queue or a workgroup the server will select the best agent to invite.
+     */
+    private String invitee;
+    /**
+     * Full JID of the user that sent the invitation.
+     */
+    private String inviter;
+    /**
+     * ID of the session that originated the initial user request.
+     */
+    private String sessionID;
+    /**
+     * JID of the room to join if offer is accepted.
+     */
+    private String room;
+    /**
+     * Text provided by the inviter explaining the reason why the invitee is invited.
+     */
+    private String reason;
+
+    public RoomTransfer(RoomTransfer.Type type, String invitee, String sessionID, String reason) {
+        this.type = type;
+        this.invitee = invitee;
+        this.sessionID = sessionID;
+        this.reason = reason;
+    }
+
+    private RoomTransfer() {
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String getInviter() {
+        return inviter;
+    }
+
+    public String getRoom() {
+        return room;
+    }
+
+    public String getReason() {
+        return reason;
+    }
+
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE);
+        buf.append("\" type=\"").append(type).append("\">");
+        buf.append("<session xmlns=\"http://jivesoftware.com/protocol/workgroup\" id=\"").append(sessionID).append("\"></session>");
+        if (invitee != null) {
+            buf.append("<invitee>").append(invitee).append("</invitee>");
+        }
+        if (inviter != null) {
+            buf.append("<inviter>").append(inviter).append("</inviter>");
+        }
+        if (reason != null) {
+            buf.append("<reason>").append(reason).append("</reason>");
+        }
+        // Add packet extensions, if any are defined.
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * Type of entity being invited to a groupchat support session.
+     */
+    public static enum Type {
+        /**
+         * A user is being invited to a groupchat support session. The user could be another agent
+         * or just a regular XMPP user.
+         */
+        user,
+        /**
+         * Some agent of the specified queue will be invited to the groupchat support session.
+         */
+        queue,
+        /**
+         * Some agent of the specified workgroup will be invited to the groupchat support session.
+         */
+        workgroup
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            final RoomTransfer invitation = new RoomTransfer();
+            invitation.type = RoomTransfer.Type.valueOf(parser.getAttributeValue("", "type"));
+
+            boolean done = false;
+            while (!done) {
+                parser.next();
+                String elementName = parser.getName();
+                if (parser.getEventType() == XmlPullParser.START_TAG) {
+                    if ("session".equals(elementName)) {
+                        invitation.sessionID = parser.getAttributeValue("", "id");
+                    }
+                    else if ("invitee".equals(elementName)) {
+                        invitation.invitee = parser.nextText();
+                    }
+                    else if ("inviter".equals(elementName)) {
+                        invitation.inviter = parser.nextText();
+                    }
+                    else if ("reason".equals(elementName)) {
+                        invitation.reason = parser.nextText();
+                    }
+                    else if ("room".equals(elementName)) {
+                        invitation.room = parser.nextText();
+                    }
+                }
+                else if (parser.getEventType() == XmlPullParser.END_TAG && ELEMENT_NAME.equals(elementName)) {
+                    done = true;
+                }
+            }
+            return invitation;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/SessionID.java b/src/org/jivesoftware/smackx/workgroup/packet/SessionID.java
new file mode 100644
index 0000000..bfd7cfd
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/SessionID.java
@@ -0,0 +1,77 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class SessionID implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "session";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    private String sessionID;
+
+    public SessionID(String sessionID) {
+        this.sessionID = sessionID;
+    }
+
+    public String getSessionID() {
+        return this.sessionID;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\" ");
+        buf.append("id=\"").append(this.getSessionID());
+        buf.append("\"/>");
+
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            String sessionID = parser.getAttributeValue("", "id");
+
+            // Advance to end of extension.
+            parser.next();
+
+            return new SessionID(sessionID);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/Transcript.java b/src/org/jivesoftware/smackx/workgroup/packet/Transcript.java
new file mode 100644
index 0000000..7f8f29e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/Transcript.java
@@ -0,0 +1,98 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+/**
+ * Represents the conversation transcript that occured in a group chat room between an Agent
+ * and a user that requested assistance. The transcript contains all the Messages that were sent
+ * to the room as well as the sent presences. 
+ *
+ * @author Gaston Dombiak
+ */
+public class Transcript extends IQ {
+    private String sessionID;
+    private List<Packet> packets;
+
+    /**
+     * Creates a transcript request for the given sessionID.
+     *
+     * @param sessionID the id of the session to get the conversation transcript.
+     */
+    public Transcript(String sessionID) {
+        this.sessionID = sessionID;
+        this.packets = new ArrayList<Packet>();
+    }
+
+    /**
+     * Creates a new transcript for the given sessionID and list of packets. The list of packets
+     * may include Messages and/or Presences.
+     *
+     * @param sessionID the id of the session that generated this conversation transcript.
+     * @param packets the list of messages and presences send to the room.
+     */
+    public Transcript(String sessionID, List<Packet> packets) {
+        this.sessionID = sessionID;
+        this.packets = packets;
+    }
+
+    /**
+     * Returns id of the session that generated this conversation transcript. The sessionID is a
+     * value generated by the server when a new request is received.
+     *
+     * @return id of the session that generated this conversation transcript.
+     */
+    public String getSessionID() {
+        return sessionID;
+    }
+
+    /**
+     * Returns the list of Messages and Presences that were sent to the room.
+     *
+     * @return the list of Messages and Presences that were sent to the room.
+     */
+    public List<Packet> getPackets() {
+        return Collections.unmodifiableList(packets);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<transcript xmlns=\"http://jivesoftware.com/protocol/workgroup\" sessionID=\"")
+                .append(sessionID)
+                .append("\">");
+
+        for (Iterator<Packet> it=packets.iterator(); it.hasNext();) {
+            Packet packet = it.next();
+            buf.append(packet.toXML());
+        }
+
+        buf.append("</transcript>");
+
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/TranscriptProvider.java b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptProvider.java
new file mode 100644
index 0000000..791b06e
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptProvider.java
@@ -0,0 +1,66 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.packet.Packet;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * An IQProvider for transcripts.
+ *
+ * @author Gaston Dombiak
+ */
+public class TranscriptProvider implements IQProvider {
+
+    public TranscriptProvider() {
+        super();
+    }
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        String sessionID = parser.getAttributeValue("", "sessionID");
+        List<Packet> packets = new ArrayList<Packet>();
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("message")) {
+                    packets.add(PacketParserUtils.parseMessage(parser));
+                }
+                else if (parser.getName().equals("presence")) {
+                    packets.add(PacketParserUtils.parsePresence(parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("transcript")) {
+                    done = true;
+                }
+            }
+        }
+
+        return new Transcript(sessionID, packets);
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/TranscriptSearch.java b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptSearch.java
new file mode 100644
index 0000000..72693c4
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptSearch.java
@@ -0,0 +1,87 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.PacketParserUtils;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * IQ packet for retrieving the transcript search form, submiting the completed search form
+ * or retrieving the answer of a transcript search.
+ *
+ * @author Gaston Dombiak
+ */
+public class TranscriptSearch extends IQ {
+
+    /**
+    * Element name of the packet extension.
+    */
+   public static final String ELEMENT_NAME = "transcript-search";
+
+   /**
+    * Namespace of the packet extension.
+    */
+   public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\">");
+        // Add packet extensions, if any are defined.
+        buf.append(getExtensionsXML());
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+
+        return buf.toString();
+    }
+
+    /**
+     * An IQProvider for TranscriptSearch packets.
+     *
+     * @author Gaston Dombiak
+     */
+    public static class Provider implements IQProvider {
+
+        public Provider() {
+            super();
+        }
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            TranscriptSearch answer = new TranscriptSearch();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if (eventType == XmlPullParser.START_TAG) {
+                    // Parse the packet extension
+                    answer.addExtension(PacketParserUtils.parsePacketExtension(parser.getName(), parser.getNamespace(), parser));
+                }
+                else if (eventType == XmlPullParser.END_TAG) {
+                    if (parser.getName().equals(ELEMENT_NAME)) {
+                        done = true;
+                    }
+                }
+            }
+
+            return answer;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/Transcripts.java b/src/org/jivesoftware/smackx/workgroup/packet/Transcripts.java
new file mode 100644
index 0000000..66ddaad
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/Transcripts.java
@@ -0,0 +1,247 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+
+import java.text.SimpleDateFormat;
+import java.util.*;
+
+/**
+ * Represents a list of conversation transcripts that a user had in all his history. Each
+ * transcript summary includes the sessionID which may be used for getting more detailed
+ * information about the conversation. {@link org.jivesoftware.smackx.workgroup.packet.Transcript}
+ *
+ * @author Gaston Dombiak
+ */
+public class Transcripts extends IQ {
+
+    private static final SimpleDateFormat UTC_FORMAT = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+    static {
+        UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("GMT+0"));
+    }
+
+    private String userID;
+    private List<Transcripts.TranscriptSummary> summaries;
+
+
+    /**
+     * Creates a transcripts request for the given userID.
+     *
+     * @param userID the id of the user to get his conversations transcripts.
+     */
+    public Transcripts(String userID) {
+        this.userID = userID;
+        this.summaries = new ArrayList<Transcripts.TranscriptSummary>();
+    }
+
+    /**
+     * Creates a Transcripts which will contain the transcript summaries of the given user.
+     *
+     * @param userID the id of the user. Could be a real JID or a unique String that identifies
+     *        anonymous users.
+     * @param summaries the list of TranscriptSummaries.
+     */
+    public Transcripts(String userID, List<Transcripts.TranscriptSummary> summaries) {
+        this.userID = userID;
+        this.summaries = summaries;
+    }
+
+    /**
+     * Returns the id of the user that was involved in the conversations. The userID could be a
+     * real JID if the connected user was not anonymous. Otherwise, the userID will be a String
+     * that was provided by the anonymous user as a way to idenitify the user across many user
+     * sessions.
+     *
+     * @return the id of the user that was involved in the conversations.
+     */
+    public String getUserID() {
+        return userID;
+    }
+
+    /**
+     * Returns a list of TranscriptSummary. A TranscriptSummary does not contain the conversation
+     * transcript but some summary information like the sessionID and the time when the
+     * conversation started and finished. Once you have the sessionID it is possible to get the
+     * full conversation transcript.
+     *
+     * @return a list of TranscriptSummary.
+     */
+    public List<Transcripts.TranscriptSummary> getSummaries() {
+        return Collections.unmodifiableList(summaries);
+    }
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<transcripts xmlns=\"http://jivesoftware.com/protocol/workgroup\" userID=\"")
+                .append(userID)
+                .append("\">");
+
+        for (TranscriptSummary transcriptSummary : summaries) {
+            buf.append(transcriptSummary.toXML());
+        }
+
+        buf.append("</transcripts>");
+
+        return buf.toString();
+    }
+
+    /**
+     * A TranscriptSummary contains some information about a conversation such as the ID of the
+     * session or the date when the conversation started and finished. You will need to use the
+     * sessionID to get the full conversation transcript.
+     */
+    public static class TranscriptSummary {
+        private String sessionID;
+        private Date joinTime;
+        private Date leftTime;
+        private List<AgentDetail> agentDetails;
+
+        public TranscriptSummary(String sessionID, Date joinTime, Date leftTime, List<AgentDetail> agentDetails) {
+            this.sessionID = sessionID;
+            this.joinTime = joinTime;
+            this.leftTime = leftTime;
+            this.agentDetails = agentDetails;
+        }
+
+        /**
+         * Returns the ID of the session that is related to this conversation transcript. The
+         * sessionID could be used for getting the full conversation transcript.
+         *
+         * @return the ID of the session that is related to this conversation transcript.
+         */
+        public String getSessionID() {
+            return sessionID;
+        }
+
+        /**
+         * Returns the Date when the conversation started.
+         *
+         * @return the Date when the conversation started.
+         */
+        public Date getJoinTime() {
+            return joinTime;
+        }
+
+        /**
+         * Returns the Date when the conversation finished.
+         *
+         * @return the Date when the conversation finished.
+         */
+        public Date getLeftTime() {
+            return leftTime;
+        }
+
+        /**
+         * Returns a list of AgentDetails. For each Agent that was involved in the conversation
+         * the list will include an AgentDetail. An AgentDetail contains the JID of the agent
+         * as well as the time when the Agent joined and left the conversation.
+         *
+         * @return a list of AgentDetails.
+         */
+        public List<AgentDetail> getAgentDetails() {
+            return agentDetails;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<transcript sessionID=\"")
+                    .append(sessionID)
+                    .append("\">");
+
+            if (joinTime != null) {
+                buf.append("<joinTime>").append(UTC_FORMAT.format(joinTime)).append("</joinTime>");
+            }
+            if (leftTime != null) {
+                buf.append("<leftTime>").append(UTC_FORMAT.format(leftTime)).append("</leftTime>");
+            }
+            buf.append("<agents>");
+            for (AgentDetail agentDetail : agentDetails) {
+                buf.append(agentDetail.toXML());
+            }
+            buf.append("</agents></transcript>");
+
+            return buf.toString();
+        }
+    }
+
+    /**
+     * An AgentDetail contains information of an Agent that was involved in a conversation. 
+     */
+    public static class AgentDetail {
+        private String agentJID;
+        private Date joinTime;
+        private Date leftTime;
+
+        public AgentDetail(String agentJID, Date joinTime, Date leftTime) {
+            this.agentJID = agentJID;
+            this.joinTime = joinTime;
+            this.leftTime = leftTime;
+        }
+
+        /**
+         * Returns the bare JID of the Agent that was involved in the conversation.
+         *
+         * @return the bared JID of the Agent that was involved in the conversation.
+         */
+        public String getAgentJID() {
+            return agentJID;
+        }
+
+        /**
+         * Returns the Date when the Agent joined the conversation.
+         *
+         * @return the Date when the Agent joined the conversation.
+         */
+        public Date getJoinTime() {
+            return joinTime;
+        }
+
+        /**
+         * Returns the Date when the Agent left the conversation.
+         *
+         * @return the Date when the Agent left the conversation.
+         */
+        public Date getLeftTime() {
+            return leftTime;
+        }
+
+        public String toXML() {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<agent>");
+
+            if (agentJID != null) {
+                buf.append("<agentJID>").append(agentJID).append("</agentJID>");
+            }
+            if (joinTime != null) {
+                buf.append("<joinTime>").append(UTC_FORMAT.format(joinTime)).append("</joinTime>");
+            }
+            if (leftTime != null) {
+                buf.append("<leftTime>").append(UTC_FORMAT.format(leftTime)).append("</leftTime>");
+            }
+            buf.append("</agent>");
+
+            return buf.toString();
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/TranscriptsProvider.java b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptsProvider.java
new file mode 100644
index 0000000..cb8f429
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/TranscriptsProvider.java
@@ -0,0 +1,148 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+import java.io.IOException;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.TimeZone;
+
+/**
+ * An IQProvider for transcripts summaries.
+ *
+ * @author Gaston Dombiak
+ */
+public class TranscriptsProvider implements IQProvider {
+
+    private static final SimpleDateFormat UTC_FORMAT = new SimpleDateFormat("yyyyMMdd'T'HH:mm:ss");
+    static {
+        UTC_FORMAT.setTimeZone(TimeZone.getTimeZone("GMT+0"));
+    }
+
+    public TranscriptsProvider() {
+        super();
+    }
+
+    public IQ parseIQ(XmlPullParser parser) throws Exception {
+        String userID = parser.getAttributeValue("", "userID");
+        List<Transcripts.TranscriptSummary> summaries = new ArrayList<Transcripts.TranscriptSummary>();
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("transcript")) {
+                    summaries.add(parseSummary(parser));
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("transcripts")) {
+                    done = true;
+                }
+            }
+        }
+
+        return new Transcripts(userID, summaries);
+    }
+
+    private Transcripts.TranscriptSummary parseSummary(XmlPullParser parser) throws IOException,
+            XmlPullParserException {
+        String sessionID =  parser.getAttributeValue("", "sessionID");
+        Date joinTime = null;
+        Date leftTime = null;
+        List<Transcripts.AgentDetail> agents = new ArrayList<Transcripts.AgentDetail>();
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("joinTime")) {
+                    try {
+                        joinTime = UTC_FORMAT.parse(parser.nextText());
+                    } catch (ParseException e) {}
+                }
+                else if (parser.getName().equals("leftTime")) {
+                    try {
+                        leftTime = UTC_FORMAT.parse(parser.nextText());
+                    } catch (ParseException e) {}
+                }
+                else if (parser.getName().equals("agents")) {
+                    agents = parseAgents(parser);
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("transcript")) {
+                    done = true;
+                }
+            }
+        }
+
+        return new Transcripts.TranscriptSummary(sessionID, joinTime, leftTime, agents);
+    }
+
+    private List<Transcripts.AgentDetail> parseAgents(XmlPullParser parser) throws IOException, XmlPullParserException {
+        List<Transcripts.AgentDetail> agents = new ArrayList<Transcripts.AgentDetail>();
+        String agentJID =  null;
+        Date joinTime = null;
+        Date leftTime = null;
+
+        boolean done = false;
+        while (!done) {
+            int eventType = parser.next();
+            if (eventType == XmlPullParser.START_TAG) {
+                if (parser.getName().equals("agentJID")) {
+                    agentJID = parser.nextText();
+                }
+                else if (parser.getName().equals("joinTime")) {
+                    try {
+                        joinTime = UTC_FORMAT.parse(parser.nextText());
+                    } catch (ParseException e) {}
+                }
+                else if (parser.getName().equals("leftTime")) {
+                    try {
+                        leftTime = UTC_FORMAT.parse(parser.nextText());
+                    } catch (ParseException e) {}
+                }
+                else if (parser.getName().equals("agent")) {
+                    agentJID =  null;
+                    joinTime = null;
+                    leftTime = null;
+                }
+            }
+            else if (eventType == XmlPullParser.END_TAG) {
+                if (parser.getName().equals("agents")) {
+                    done = true;
+                }
+                else if (parser.getName().equals("agent")) {
+                    agents.add(new Transcripts.AgentDetail(agentJID, joinTime, leftTime));
+                }
+            }
+        }
+        return agents;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/UserID.java b/src/org/jivesoftware/smackx/workgroup/packet/UserID.java
new file mode 100644
index 0000000..8bf4589
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/UserID.java
@@ -0,0 +1,77 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class UserID implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "user";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    private String userID;
+
+    public UserID(String userID) {
+        this.userID = userID;
+    }
+
+    public String getUserID() {
+        return this.userID;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=\"").append(NAMESPACE).append("\" ");
+        buf.append("id=\"").append(this.getUserID());
+        buf.append("\"/>");
+
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        public PacketExtension parseExtension(XmlPullParser parser) throws Exception {
+            String userID = parser.getAttributeValue("", "id");
+
+            // Advance to end of extension.
+            parser.next();
+
+            return new UserID(userID);
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/packet/WorkgroupInformation.java b/src/org/jivesoftware/smackx/workgroup/packet/WorkgroupInformation.java
new file mode 100644
index 0000000..b0ea447
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/packet/WorkgroupInformation.java
@@ -0,0 +1,86 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.packet;
+
+import org.jivesoftware.smack.packet.PacketExtension;
+import org.jivesoftware.smack.provider.PacketExtensionProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+/**
+ * A packet extension that contains information about the user and agent in a
+ * workgroup chat. The packet extension is attached to group chat invitations.
+ */
+public class WorkgroupInformation implements PacketExtension {
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "workgroup";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jabber.org/protocol/workgroup";
+
+    private String workgroupJID;
+
+    public WorkgroupInformation(String workgroupJID){
+        this.workgroupJID = workgroupJID;
+    }
+
+    public String getWorkgroupJID() {
+        return workgroupJID;
+    }
+
+    public String getElementName() {
+        return ELEMENT_NAME;
+    }
+
+    public String getNamespace() {
+        return NAMESPACE;
+    }
+
+    public String toXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append('<').append(ELEMENT_NAME);
+        buf.append(" jid=\"").append(getWorkgroupJID()).append("\"");
+        buf.append(" xmlns=\"").append(NAMESPACE).append("\" />");
+
+        return buf.toString();
+    }
+
+    public static class Provider implements PacketExtensionProvider {
+
+        /**
+         * PacketExtensionProvider implementation
+         */
+        public PacketExtension parseExtension (XmlPullParser parser)
+            throws Exception {
+            String workgroupJID = parser.getAttributeValue("", "jid");
+
+            // since this is a start and end tag, and we arrive on the start, this should guarantee
+            //      we leave on the end
+            parser.next();
+
+            return new WorkgroupInformation(workgroupJID);
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/ChatSetting.java b/src/org/jivesoftware/smackx/workgroup/settings/ChatSetting.java
new file mode 100644
index 0000000..921134a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/ChatSetting.java
@@ -0,0 +1,56 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+public class ChatSetting {
+    private String key;
+    private String value;
+    private int type;
+
+    public ChatSetting(String key, String value, int type){
+        setKey(key);
+        setValue(value);
+        setType(type);
+    }
+
+    public String getKey() {
+        return key;
+    }
+
+    public void setKey(String key) {
+        this.key = key;
+    }
+
+    public String getValue() {
+        return value;
+    }
+
+    public void setValue(String value) {
+        this.value = value;
+    }
+
+    public int getType() {
+        return type;
+    }
+
+    public void setType(int type) {
+        this.type = type;
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/ChatSettings.java b/src/org/jivesoftware/smackx/workgroup/settings/ChatSettings.java
new file mode 100644
index 0000000..ccc7a40
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/ChatSettings.java
@@ -0,0 +1,179 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+
+public class ChatSettings extends IQ {
+
+    /**
+     * Defined as image type.
+     */
+    public static final int IMAGE_SETTINGS = 0;
+
+    /**
+     * Defined as Text settings type.
+     */
+    public static final int TEXT_SETTINGS = 1;
+
+    /**
+     * Defined as Bot settings type.
+     */
+    public static final int BOT_SETTINGS = 2;
+
+    private List<ChatSetting> settings;
+    private String key;
+    private int type = -1;
+
+    public ChatSettings() {
+        settings = new ArrayList<ChatSetting>();
+    }
+
+    public ChatSettings(String key) {
+        setKey(key);
+    }
+
+    public void setKey(String key) {
+        this.key = key;
+    }
+
+    public void setType(int type) {
+        this.type = type;
+    }
+
+    public void addSetting(ChatSetting setting) {
+        settings.add(setting);
+    }
+
+    public Collection<ChatSetting> getSettings() {
+        return settings;
+    }
+
+    public ChatSetting getChatSetting(String key) {
+        Collection<ChatSetting> col = getSettings();
+        if (col != null) {
+            Iterator<ChatSetting> iter = col.iterator();
+            while (iter.hasNext()) {
+                ChatSetting chatSetting = iter.next();
+                if (chatSetting.getKey().equals(key)) {
+                    return chatSetting;
+                }
+            }
+        }
+        return null;
+    }
+
+    public ChatSetting getFirstEntry() {
+        if (settings.size() > 0) {
+            return (ChatSetting)settings.get(0);
+        }
+        return null;
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "chat-settings";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        if (key != null) {
+            buf.append(" key=\"" + key + "\"");
+        }
+
+        if (type != -1) {
+            buf.append(" type=\"" + type + "\"");
+        }
+
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+    /**
+     * Packet extension provider for AgentStatusRequest packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            ChatSettings chatSettings = new ChatSettings();
+
+            boolean done = false;
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("chat-setting".equals(parser.getName()))) {
+                    chatSettings.addSetting(parseChatSetting(parser));
+
+                }
+                else if (eventType == XmlPullParser.END_TAG && ELEMENT_NAME.equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return chatSettings;
+        }
+
+        private ChatSetting parseChatSetting(XmlPullParser parser) throws Exception {
+
+            boolean done = false;
+            String key = null;
+            String value = null;
+            int type = 0;
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("key".equals(parser.getName()))) {
+                    key = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("value".equals(parser.getName()))) {
+                    value = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("type".equals(parser.getName()))) {
+                    type = Integer.parseInt(parser.nextText());
+                }
+                else if (eventType == XmlPullParser.END_TAG && "chat-setting".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+            return new ChatSetting(key, value, type);
+        }
+    }
+}
+
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/GenericSettings.java b/src/org/jivesoftware/smackx/workgroup/settings/GenericSettings.java
new file mode 100644
index 0000000..702eeb7
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/GenericSettings.java
@@ -0,0 +1,114 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smackx.workgroup.util.ModelUtil;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class GenericSettings extends IQ {
+
+    private Map<String, String> map = new HashMap<String, String>();
+
+    private String query;
+
+    public String getQuery() {
+        return query;
+    }
+
+    public void setQuery(String query) {
+        this.query = query;
+    }
+
+    public Map<String, String> getMap() {
+        return map;
+    }
+
+    public void setMap(Map<String, String> map) {
+        this.map = map;
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "generic-metadata";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append(">");
+        if (ModelUtil.hasLength(getQuery())) {
+            buf.append("<query>" + getQuery() + "</query>");
+        }
+        buf.append("</").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+
+    /**
+     * Packet extension provider for SoundSetting Packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            GenericSettings setting = new GenericSettings();
+
+            boolean done = false;
+
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("entry".equals(parser.getName()))) {
+                    eventType = parser.next();
+                    String name = parser.nextText();
+                    eventType = parser.next();
+                    String value = parser.nextText();
+                    setting.getMap().put(name, value);
+                }
+                else if (eventType == XmlPullParser.END_TAG && ELEMENT_NAME.equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            return setting;
+        }
+    }
+
+
+}
+
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/OfflineSettings.java b/src/org/jivesoftware/smackx/workgroup/settings/OfflineSettings.java
new file mode 100644
index 0000000..15136fd
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/OfflineSettings.java
@@ -0,0 +1,155 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smackx.workgroup.util.ModelUtil;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class OfflineSettings extends IQ {
+    private String redirectURL;
+
+    private String offlineText;
+    private String emailAddress;
+    private String subject;
+
+    public String getRedirectURL() {
+        if (!ModelUtil.hasLength(redirectURL)) {
+            return "";
+        }
+        return redirectURL;
+    }
+
+    public void setRedirectURL(String redirectURL) {
+        this.redirectURL = redirectURL;
+    }
+
+    public String getOfflineText() {
+        if (!ModelUtil.hasLength(offlineText)) {
+            return "";
+        }
+        return offlineText;
+    }
+
+    public void setOfflineText(String offlineText) {
+        this.offlineText = offlineText;
+    }
+
+    public String getEmailAddress() {
+        if (!ModelUtil.hasLength(emailAddress)) {
+            return "";
+        }
+        return emailAddress;
+    }
+
+    public void setEmailAddress(String emailAddress) {
+        this.emailAddress = emailAddress;
+    }
+
+    public String getSubject() {
+        if (!ModelUtil.hasLength(subject)) {
+            return "";
+        }
+        return subject;
+    }
+
+    public void setSubject(String subject) {
+        this.subject = subject;
+    }
+
+    public boolean redirects() {
+        return (ModelUtil.hasLength(getRedirectURL()));
+    }
+
+    public boolean isConfigured(){
+        return ModelUtil.hasLength(getEmailAddress()) &&
+               ModelUtil.hasLength(getSubject()) &&
+               ModelUtil.hasLength(getOfflineText());
+    }
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "offline-settings";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+
+    /**
+     * Packet extension provider for AgentStatusRequest packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            OfflineSettings offlineSettings = new OfflineSettings();
+
+            boolean done = false;
+            String redirectPage = null;
+            String subject = null;
+            String offlineText = null;
+            String emailAddress = null;
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("redirectPage".equals(parser.getName()))) {
+                    redirectPage = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("subject".equals(parser.getName()))) {
+                    subject = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("offlineText".equals(parser.getName()))) {
+                    offlineText = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("emailAddress".equals(parser.getName()))) {
+                    emailAddress = parser.nextText();
+                }
+                else if (eventType == XmlPullParser.END_TAG && "offline-settings".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            offlineSettings.setEmailAddress(emailAddress);
+            offlineSettings.setRedirectURL(redirectPage);
+            offlineSettings.setSubject(subject);
+            offlineSettings.setOfflineText(offlineText);
+            return offlineSettings;
+        }
+    }
+}
+
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/SearchSettings.java b/src/org/jivesoftware/smackx/workgroup/settings/SearchSettings.java
new file mode 100644
index 0000000..98d59fc
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/SearchSettings.java
@@ -0,0 +1,112 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smackx.workgroup.util.ModelUtil;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class SearchSettings extends IQ {
+    private String forumsLocation;
+    private String kbLocation;
+
+    public boolean isSearchEnabled() {
+        return ModelUtil.hasLength(getForumsLocation()) && ModelUtil.hasLength(getKbLocation());
+    }
+
+    public String getForumsLocation() {
+        return forumsLocation;
+    }
+
+    public void setForumsLocation(String forumsLocation) {
+        this.forumsLocation = forumsLocation;
+    }
+
+    public String getKbLocation() {
+        return kbLocation;
+    }
+
+    public void setKbLocation(String kbLocation) {
+        this.kbLocation = kbLocation;
+    }
+
+    public boolean hasKB(){
+        return ModelUtil.hasLength(getKbLocation());
+    }
+
+    public boolean hasForums(){
+        return ModelUtil.hasLength(getForumsLocation());
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "search-settings";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+
+    /**
+     * Packet extension provider for AgentStatusRequest packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            SearchSettings settings = new SearchSettings();
+
+            boolean done = false;
+            String kb = null;
+            String forums = null;
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("forums".equals(parser.getName()))) {
+                    forums = parser.nextText();
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("kb".equals(parser.getName()))) {
+                    kb = parser.nextText();
+                }
+                else if (eventType == XmlPullParser.END_TAG && "search-settings".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            settings.setForumsLocation(forums);
+            settings.setKbLocation(kb);
+            return settings;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/SoundSettings.java b/src/org/jivesoftware/smackx/workgroup/settings/SoundSettings.java
new file mode 100644
index 0000000..66bec35
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/SoundSettings.java
@@ -0,0 +1,103 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.jivesoftware.smack.util.StringUtils;
+import org.xmlpull.v1.XmlPullParser;
+
+public class SoundSettings extends IQ {
+    private String outgoingSound;
+    private String incomingSound;
+
+
+    public void setOutgoingSound(String outgoingSound) {
+        this.outgoingSound = outgoingSound;
+    }
+
+    public void setIncomingSound(String incomingSound) {
+        this.incomingSound = incomingSound;
+    }
+
+    public byte[] getIncomingSoundBytes() {
+        return StringUtils.decodeBase64(incomingSound);
+    }
+
+    public byte[] getOutgoingSoundBytes() {
+        return StringUtils.decodeBase64(outgoingSound);
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "sound-settings";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+
+    /**
+     * Packet extension provider for SoundSetting Packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            SoundSettings soundSettings = new SoundSettings();
+
+            boolean done = false;
+
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("outgoingSound".equals(parser.getName()))) {
+                    soundSettings.setOutgoingSound(parser.nextText());
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("incomingSound".equals(parser.getName()))) {
+                    soundSettings.setIncomingSound(parser.nextText());
+                }
+                else if (eventType == XmlPullParser.END_TAG && "sound-settings".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            return soundSettings;
+        }
+    }
+}
+
diff --git a/src/org/jivesoftware/smackx/workgroup/settings/WorkgroupProperties.java b/src/org/jivesoftware/smackx/workgroup/settings/WorkgroupProperties.java
new file mode 100644
index 0000000..8e405bb
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/settings/WorkgroupProperties.java
@@ -0,0 +1,125 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.settings;
+
+import org.jivesoftware.smackx.workgroup.util.ModelUtil;
+import org.jivesoftware.smack.packet.IQ;
+import org.jivesoftware.smack.provider.IQProvider;
+import org.xmlpull.v1.XmlPullParser;
+
+public class WorkgroupProperties extends IQ {
+
+    private boolean authRequired;
+    private String email;
+    private String fullName;
+    private String jid;
+
+    public boolean isAuthRequired() {
+        return authRequired;
+    }
+
+    public void setAuthRequired(boolean authRequired) {
+        this.authRequired = authRequired;
+    }
+
+    public String getEmail() {
+        return email;
+    }
+
+    public void setEmail(String email) {
+        this.email = email;
+    }
+
+    public String getFullName() {
+        return fullName;
+    }
+
+    public void setFullName(String fullName) {
+        this.fullName = fullName;
+    }
+
+    public String getJid() {
+        return jid;
+    }
+
+    public void setJid(String jid) {
+        this.jid = jid;
+    }
+
+
+    /**
+     * Element name of the packet extension.
+     */
+    public static final String ELEMENT_NAME = "workgroup-properties";
+
+    /**
+     * Namespace of the packet extension.
+     */
+    public static final String NAMESPACE = "http://jivesoftware.com/protocol/workgroup";
+
+    public String getChildElementXML() {
+        StringBuilder buf = new StringBuilder();
+
+        buf.append("<").append(ELEMENT_NAME).append(" xmlns=");
+        buf.append('"');
+        buf.append(NAMESPACE);
+        buf.append('"');
+        if (ModelUtil.hasLength(getJid())) {
+            buf.append("jid=\"" + getJid() + "\" ");
+        }
+        buf.append("></").append(ELEMENT_NAME).append("> ");
+        return buf.toString();
+    }
+
+    /**
+     * Packet extension provider for SoundSetting Packets.
+     */
+    public static class InternalProvider implements IQProvider {
+
+        public IQ parseIQ(XmlPullParser parser) throws Exception {
+            if (parser.getEventType() != XmlPullParser.START_TAG) {
+                throw new IllegalStateException("Parser not in proper position, or bad XML.");
+            }
+
+            WorkgroupProperties props = new WorkgroupProperties();
+
+            boolean done = false;
+
+
+            while (!done) {
+                int eventType = parser.next();
+                if ((eventType == XmlPullParser.START_TAG) && ("authRequired".equals(parser.getName()))) {
+                    props.setAuthRequired(new Boolean(parser.nextText()).booleanValue());
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("email".equals(parser.getName()))) {
+                    props.setEmail(parser.nextText());
+                }
+                else if ((eventType == XmlPullParser.START_TAG) && ("name".equals(parser.getName()))) {
+                    props.setFullName(parser.nextText());
+                }
+                else if (eventType == XmlPullParser.END_TAG && "workgroup-properties".equals(parser.getName())) {
+                    done = true;
+                }
+            }
+
+            return props;
+        }
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/user/QueueListener.java b/src/org/jivesoftware/smackx/workgroup/user/QueueListener.java
new file mode 100644
index 0000000..fa3e6a6
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/user/QueueListener.java
@@ -0,0 +1,55 @@
+/**
+ * $Revision$
+ * $Date$
+ *
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.user;
+
+/**
+ * Listener interface for those that wish to be notified of workgroup queue events.
+ *
+ * @see Workgroup#addQueueListener(QueueListener)
+ * @author loki der quaeler
+ */
+public interface QueueListener {
+
+    /**
+     * The user joined the workgroup queue.
+     */
+    public void joinedQueue();
+
+    /**
+     * The user departed the workgroup queue.
+     */
+    public void departedQueue();
+
+    /**
+     * The user's queue position has been updated to a new value.
+     *
+     * @param currentPosition the user's current position in the queue.
+     */
+    public void queuePositionUpdated(int currentPosition);
+
+    /**
+     * The user's estimated remaining wait time in the queue has been updated.
+     *
+     * @param secondsRemaining the estimated number of seconds remaining until the
+     *      the user is routed to the agent.
+     */
+    public void queueWaitTimeUpdated(int secondsRemaining);
+
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/user/Workgroup.java b/src/org/jivesoftware/smackx/workgroup/user/Workgroup.java
new file mode 100644
index 0000000..237337f
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/user/Workgroup.java
@@ -0,0 +1,868 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.user;
+
+import org.jivesoftware.smackx.workgroup.MetaData;
+import org.jivesoftware.smackx.workgroup.WorkgroupInvitation;
+import org.jivesoftware.smackx.workgroup.WorkgroupInvitationListener;
+import org.jivesoftware.smackx.workgroup.ext.forms.WorkgroupForm;
+import org.jivesoftware.smackx.workgroup.packet.DepartQueuePacket;
+import org.jivesoftware.smackx.workgroup.packet.QueueUpdate;
+import org.jivesoftware.smackx.workgroup.packet.SessionID;
+import org.jivesoftware.smackx.workgroup.packet.UserID;
+import org.jivesoftware.smackx.workgroup.settings.*;
+import org.jivesoftware.smack.*;
+import org.jivesoftware.smack.filter.*;
+import org.jivesoftware.smack.packet.*;
+import org.jivesoftware.smack.util.StringUtils;
+import org.jivesoftware.smackx.Form;
+import org.jivesoftware.smackx.FormField;
+import org.jivesoftware.smackx.ServiceDiscoveryManager;
+import org.jivesoftware.smackx.muc.MultiUserChat;
+import org.jivesoftware.smackx.packet.DataForm;
+import org.jivesoftware.smackx.packet.DiscoverInfo;
+import org.jivesoftware.smackx.packet.MUCUser;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Provides workgroup services for users. Users can join the workgroup queue, depart the
+ * queue, find status information about their placement in the queue, and register to
+ * be notified when they are routed to an agent.<p>
+ * <p/>
+ * This class only provides a users perspective into a workgroup and is not intended
+ * for use by agents.
+ *
+ * @author Matt Tucker
+ * @author Derek DeMoro
+ */
+public class Workgroup {
+
+    private String workgroupJID;
+    private Connection connection;
+    private boolean inQueue;
+    private List<WorkgroupInvitationListener> invitationListeners;
+    private List<QueueListener> queueListeners;
+
+    private int queuePosition = -1;
+    private int queueRemainingTime = -1;
+
+    /**
+     * Creates a new workgroup instance using the specified workgroup JID
+     * (eg support@workgroup.example.com) and XMPP connection. The connection must have
+     * undergone a successful login before being used to construct an instance of
+     * this class.
+     *
+     * @param workgroupJID the JID of the workgroup.
+     * @param connection   an XMPP connection which must have already undergone a
+     *                     successful login.
+     */
+    public Workgroup(String workgroupJID, Connection connection) {
+        // Login must have been done before passing in connection.
+        if (!connection.isAuthenticated()) {
+            throw new IllegalStateException("Must login to server before creating workgroup.");
+        }
+
+        this.workgroupJID = workgroupJID;
+        this.connection = connection;
+        inQueue = false;
+        invitationListeners = new ArrayList<WorkgroupInvitationListener>();
+        queueListeners = new ArrayList<QueueListener>();
+
+        // Register as a queue listener for internal usage by this instance.
+        addQueueListener(new QueueListener() {
+            public void joinedQueue() {
+                inQueue = true;
+            }
+
+            public void departedQueue() {
+                inQueue = false;
+                queuePosition = -1;
+                queueRemainingTime = -1;
+            }
+
+            public void queuePositionUpdated(int currentPosition) {
+                queuePosition = currentPosition;
+            }
+
+            public void queueWaitTimeUpdated(int secondsRemaining) {
+                queueRemainingTime = secondsRemaining;
+            }
+        });
+
+        /**
+         * Internal handling of an invitation.Recieving an invitation removes the user from the queue.
+         */
+        MultiUserChat.addInvitationListener(connection,
+                new org.jivesoftware.smackx.muc.InvitationListener() {
+                    public void invitationReceived(Connection conn, String room, String inviter,
+                                                   String reason, String password, Message message) {
+                        inQueue = false;
+                        queuePosition = -1;
+                        queueRemainingTime = -1;
+                    }
+                });
+
+        // Register a packet listener for all the messages sent to this client.
+        PacketFilter typeFilter = new PacketTypeFilter(Message.class);
+
+        connection.addPacketListener(new PacketListener() {
+            public void processPacket(Packet packet) {
+                handlePacket(packet);
+            }
+        }, typeFilter);
+    }
+
+    /**
+     * Returns the name of this workgroup (eg support@example.com).
+     *
+     * @return the name of the workgroup.
+     */
+    public String getWorkgroupJID() {
+        return workgroupJID;
+    }
+
+    /**
+     * Returns true if the user is currently waiting in the workgroup queue.
+     *
+     * @return true if currently waiting in the queue.
+     */
+    public boolean isInQueue() {
+        return inQueue;
+    }
+
+    /**
+     * Returns true if the workgroup is available for receiving new requests. The workgroup will be
+     * available only when agents are available for this workgroup.
+     *
+     * @return true if the workgroup is available for receiving new requests.
+     */
+    public boolean isAvailable() {
+        Presence directedPresence = new Presence(Presence.Type.available);
+        directedPresence.setTo(workgroupJID);
+        PacketFilter typeFilter = new PacketTypeFilter(Presence.class);
+        PacketFilter fromFilter = new FromContainsFilter(workgroupJID);
+        PacketCollector collector = connection.createPacketCollector(new AndFilter(fromFilter,
+                typeFilter));
+
+        connection.sendPacket(directedPresence);
+
+        Presence response = (Presence)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            return false;
+        }
+        else if (response.getError() != null) {
+            return false;
+        }
+        else {
+            return Presence.Type.available == response.getType();
+        }
+    }
+
+    /**
+     * Returns the users current position in the workgroup queue. A value of 0 means
+     * the user is next in line to be routed; therefore, if the queue position
+     * is being displayed to the end user it is usually a good idea to add 1 to
+     * the value this method returns before display. If the user is not currently
+     * waiting in the workgroup, or no queue position information is available, -1
+     * will be returned.
+     *
+     * @return the user's current position in the workgroup queue, or -1 if the
+     *         position isn't available or if the user isn't in the queue.
+     */
+    public int getQueuePosition() {
+        return queuePosition;
+    }
+
+    /**
+     * Returns the estimated time (in seconds) that the user has to left wait in
+     * the workgroup queue before being routed. If the user is not currently waiting
+     * int he workgroup, or no queue time information is available, -1 will be
+     * returned.
+     *
+     * @return the estimated time remaining (in seconds) that the user has to
+     *         wait inthe workgroupu queue, or -1 if time information isn't available
+     *         or if the user isn't int the queue.
+     */
+    public int getQueueRemainingTime() {
+        return queueRemainingTime;
+    }
+
+    /**
+     * Joins the workgroup queue to wait to be routed to an agent. After joining
+     * the queue, queue status events will be sent to indicate the user's position and
+     * estimated time left in the queue. Once joining the queue, there are three ways
+     * the user can leave the queue: <ul>
+     * <p/>
+     * <li>The user is routed to an agent, which triggers a GroupChat invitation.
+     * <li>The user asks to leave the queue by calling the {@link #departQueue} method.
+     * <li>A server error occurs, or an administrator explicitly removes the user
+     * from the queue.
+     * </ul>
+     * <p/>
+     * A user cannot request to join the queue again if already in the queue. Therefore,
+     * this method will throw an IllegalStateException if the user is already in the queue.<p>
+     * <p/>
+     * Some servers may be configured to require certain meta-data in order to
+     * join the queue. In that case, the {@link #joinQueue(Form)} method should be
+     * used instead of this method so that meta-data may be passed in.<p>
+     * <p/>
+     * The server tracks the conversations that a user has with agents over time. By
+     * default, that tracking is done using the user's JID. However, this is not always
+     * possible. For example, when the user is logged in anonymously using a web client.
+     * In that case the user ID might be a randomly generated value put into a persistent
+     * cookie or a username obtained via the session. A userID can be explicitly
+     * passed in by using the {@link #joinQueue(Form, String)} method. When specified,
+     * that userID will be used instead of the user's JID to track conversations. The
+     * server will ignore a manually specified userID if the user's connection to the server
+     * is not anonymous.
+     *
+     * @throws XMPPException if an error occured joining the queue. An error may indicate
+     *                       that a connection failure occured or that the server explicitly rejected the
+     *                       request to join the queue.
+     */
+    public void joinQueue() throws XMPPException {
+        joinQueue(null);
+    }
+
+    /**
+     * Joins the workgroup queue to wait to be routed to an agent. After joining
+     * the queue, queue status events will be sent to indicate the user's position and
+     * estimated time left in the queue. Once joining the queue, there are three ways
+     * the user can leave the queue: <ul>
+     * <p/>
+     * <li>The user is routed to an agent, which triggers a GroupChat invitation.
+     * <li>The user asks to leave the queue by calling the {@link #departQueue} method.
+     * <li>A server error occurs, or an administrator explicitly removes the user
+     * from the queue.
+     * </ul>
+     * <p/>
+     * A user cannot request to join the queue again if already in the queue. Therefore,
+     * this method will throw an IllegalStateException if the user is already in the queue.<p>
+     * <p/>
+     * Some servers may be configured to require certain meta-data in order to
+     * join the queue.<p>
+     * <p/>
+     * The server tracks the conversations that a user has with agents over time. By
+     * default, that tracking is done using the user's JID. However, this is not always
+     * possible. For example, when the user is logged in anonymously using a web client.
+     * In that case the user ID might be a randomly generated value put into a persistent
+     * cookie or a username obtained via the session. A userID can be explicitly
+     * passed in by using the {@link #joinQueue(Form, String)} method. When specified,
+     * that userID will be used instead of the user's JID to track conversations. The
+     * server will ignore a manually specified userID if the user's connection to the server
+     * is not anonymous.
+     *
+     * @param answerForm the completed form the send for the join request.
+     * @throws XMPPException if an error occured joining the queue. An error may indicate
+     *                       that a connection failure occured or that the server explicitly rejected the
+     *                       request to join the queue.
+     */
+    public void joinQueue(Form answerForm) throws XMPPException {
+        joinQueue(answerForm, null);
+    }
+
+    /**
+     * <p>Joins the workgroup queue to wait to be routed to an agent. After joining
+     * the queue, queue status events will be sent to indicate the user's position and
+     * estimated time left in the queue. Once joining the queue, there are three ways
+     * the user can leave the queue: <ul>
+     * <p/>
+     * <li>The user is routed to an agent, which triggers a GroupChat invitation.
+     * <li>The user asks to leave the queue by calling the {@link #departQueue} method.
+     * <li>A server error occurs, or an administrator explicitly removes the user
+     * from the queue.
+     * </ul>
+     * <p/>
+     * A user cannot request to join the queue again if already in the queue. Therefore,
+     * this method will throw an IllegalStateException if the user is already in the queue.<p>
+     * <p/>
+     * Some servers may be configured to require certain meta-data in order to
+     * join the queue.<p>
+     * <p/>
+     * The server tracks the conversations that a user has with agents over time. By
+     * default, that tracking is done using the user's JID. However, this is not always
+     * possible. For example, when the user is logged in anonymously using a web client.
+     * In that case the user ID might be a randomly generated value put into a persistent
+     * cookie or a username obtained via the session. When specified, that userID will
+     * be used instead of the user's JID to track conversations. The server will ignore a
+     * manually specified userID if the user's connection to the server is not anonymous.
+     *
+     * @param answerForm the completed form associated with the join reqest.
+     * @param userID     String that represents the ID of the user when using anonymous sessions
+     *                   or <tt>null</tt> if a userID should not be used.
+     * @throws XMPPException if an error occured joining the queue. An error may indicate
+     *                       that a connection failure occured or that the server explicitly rejected the
+     *                       request to join the queue.
+     */
+    public void joinQueue(Form answerForm, String userID) throws XMPPException {
+        // If already in the queue ignore the join request.
+        if (inQueue) {
+            throw new IllegalStateException("Already in queue " + workgroupJID);
+        }
+
+        JoinQueuePacket joinPacket = new JoinQueuePacket(workgroupJID, answerForm, userID);
+
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(joinPacket.getPacketID()));
+
+        this.connection.sendPacket(joinPacket);
+
+        IQ response = (IQ)collector.nextResult(10000);
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+
+        // Notify listeners that we've joined the queue.
+        fireQueueJoinedEvent();
+    }
+
+    /**
+     * <p>Joins the workgroup queue to wait to be routed to an agent. After joining
+     * the queue, queue status events will be sent to indicate the user's position and
+     * estimated time left in the queue. Once joining the queue, there are three ways
+     * the user can leave the queue: <ul>
+     * <p/>
+     * <li>The user is routed to an agent, which triggers a GroupChat invitation.
+     * <li>The user asks to leave the queue by calling the {@link #departQueue} method.
+     * <li>A server error occurs, or an administrator explicitly removes the user
+     * from the queue.
+     * </ul>
+     * <p/>
+     * A user cannot request to join the queue again if already in the queue. Therefore,
+     * this method will throw an IllegalStateException if the user is already in the queue.<p>
+     * <p/>
+     * Some servers may be configured to require certain meta-data in order to
+     * join the queue.<p>
+     * <p/>
+     * The server tracks the conversations that a user has with agents over time. By
+     * default, that tracking is done using the user's JID. However, this is not always
+     * possible. For example, when the user is logged in anonymously using a web client.
+     * In that case the user ID might be a randomly generated value put into a persistent
+     * cookie or a username obtained via the session. When specified, that userID will
+     * be used instead of the user's JID to track conversations. The server will ignore a
+     * manually specified userID if the user's connection to the server is not anonymous.
+     *
+     * @param metadata metadata to create a dataform from.
+     * @param userID   String that represents the ID of the user when using anonymous sessions
+     *                 or <tt>null</tt> if a userID should not be used.
+     * @throws XMPPException if an error occured joining the queue. An error may indicate
+     *                       that a connection failure occured or that the server explicitly rejected the
+     *                       request to join the queue.
+     */
+    public void joinQueue(Map<String,Object> metadata, String userID) throws XMPPException {
+        // If already in the queue ignore the join request.
+        if (inQueue) {
+            throw new IllegalStateException("Already in queue " + workgroupJID);
+        }
+
+        // Build dataform from metadata
+        Form form = new Form(Form.TYPE_SUBMIT);
+        Iterator<String> iter = metadata.keySet().iterator();
+        while (iter.hasNext()) {
+            String name = iter.next();
+            String value = metadata.get(name).toString();
+
+            String escapedName = StringUtils.escapeForXML(name);
+            String escapedValue = StringUtils.escapeForXML(value);
+
+            FormField field = new FormField(escapedName);
+            field.setType(FormField.TYPE_TEXT_SINGLE);
+            form.addField(field);
+            form.setAnswer(escapedName, escapedValue);
+        }
+        joinQueue(form, userID);
+    }
+
+    /**
+     * Departs the workgroup queue. If the user is not currently in the queue, this
+     * method will do nothing.<p>
+     * <p/>
+     * Normally, the user would not manually leave the queue. However, they may wish to
+     * under certain circumstances -- for example, if they no longer wish to be routed
+     * to an agent because they've been waiting too long.
+     *
+     * @throws XMPPException if an error occured trying to send the depart queue
+     *                       request to the server.
+     */
+    public void departQueue() throws XMPPException {
+        // If not in the queue ignore the depart request.
+        if (!inQueue) {
+            return;
+        }
+
+        DepartQueuePacket departPacket = new DepartQueuePacket(this.workgroupJID);
+        PacketCollector collector = this.connection.createPacketCollector(new PacketIDFilter(departPacket.getPacketID()));
+
+        connection.sendPacket(departPacket);
+
+        IQ response = (IQ)collector.nextResult(5000);
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from the server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+
+        // Notify listeners that we're no longer in the queue.
+        fireQueueDepartedEvent();
+    }
+
+    /**
+     * Adds a queue listener that will be notified of queue events for the user
+     * that created this Workgroup instance.
+     *
+     * @param queueListener the queue listener.
+     */
+    public void addQueueListener(QueueListener queueListener) {
+        synchronized (queueListeners) {
+            if (!queueListeners.contains(queueListener)) {
+                queueListeners.add(queueListener);
+            }
+        }
+    }
+
+    /**
+     * Removes a queue listener.
+     *
+     * @param queueListener the queue listener.
+     */
+    public void removeQueueListener(QueueListener queueListener) {
+        synchronized (queueListeners) {
+            queueListeners.remove(queueListener);
+        }
+    }
+
+    /**
+     * Adds an invitation listener that will be notified of groupchat invitations
+     * from the workgroup for the the user that created this Workgroup instance.
+     *
+     * @param invitationListener the invitation listener.
+     */
+    public void addInvitationListener(WorkgroupInvitationListener invitationListener) {
+        synchronized (invitationListeners) {
+            if (!invitationListeners.contains(invitationListener)) {
+                invitationListeners.add(invitationListener);
+            }
+        }
+    }
+
+    /**
+     * Removes an invitation listener.
+     *
+     * @param invitationListener the invitation listener.
+     */
+    public void removeQueueListener(WorkgroupInvitationListener invitationListener) {
+        synchronized (invitationListeners) {
+            invitationListeners.remove(invitationListener);
+        }
+    }
+
+    private void fireInvitationEvent(WorkgroupInvitation invitation) {
+        synchronized (invitationListeners) {
+            for (Iterator<WorkgroupInvitationListener> i = invitationListeners.iterator(); i.hasNext();) {
+                WorkgroupInvitationListener listener = i.next();
+                listener.invitationReceived(invitation);
+            }
+        }
+    }
+
+    private void fireQueueJoinedEvent() {
+        synchronized (queueListeners) {
+            for (Iterator<QueueListener> i = queueListeners.iterator(); i.hasNext();) {
+                QueueListener listener = i.next();
+                listener.joinedQueue();
+            }
+        }
+    }
+
+    private void fireQueueDepartedEvent() {
+        synchronized (queueListeners) {
+            for (Iterator<QueueListener> i = queueListeners.iterator(); i.hasNext();) {
+                QueueListener listener = i.next();
+                listener.departedQueue();
+            }
+        }
+    }
+
+    private void fireQueuePositionEvent(int currentPosition) {
+        synchronized (queueListeners) {
+            for (Iterator<QueueListener> i = queueListeners.iterator(); i.hasNext();) {
+                QueueListener listener = i.next();
+                listener.queuePositionUpdated(currentPosition);
+            }
+        }
+    }
+
+    private void fireQueueTimeEvent(int secondsRemaining) {
+        synchronized (queueListeners) {
+            for (Iterator<QueueListener> i = queueListeners.iterator(); i.hasNext();) {
+                QueueListener listener = i.next();
+                listener.queueWaitTimeUpdated(secondsRemaining);
+            }
+        }
+    }
+
+    // PacketListener Implementation.
+
+    private void handlePacket(Packet packet) {
+        if (packet instanceof Message) {
+            Message msg = (Message)packet;
+            // Check to see if the user left the queue.
+            PacketExtension pe = msg.getExtension("depart-queue", "http://jabber.org/protocol/workgroup");
+            PacketExtension queueStatus = msg.getExtension("queue-status", "http://jabber.org/protocol/workgroup");
+
+            if (pe != null) {
+                fireQueueDepartedEvent();
+            }
+            else if (queueStatus != null) {
+                QueueUpdate queueUpdate = (QueueUpdate)queueStatus;
+                if (queueUpdate.getPosition() != -1) {
+                    fireQueuePositionEvent(queueUpdate.getPosition());
+                }
+                if (queueUpdate.getRemaingTime() != -1) {
+                    fireQueueTimeEvent(queueUpdate.getRemaingTime());
+                }
+            }
+
+            else {
+                // Check if a room invitation was sent and if the sender is the workgroup
+                MUCUser mucUser = (MUCUser)msg.getExtension("x", "http://jabber.org/protocol/muc#user");
+                MUCUser.Invite invite = mucUser != null ? mucUser.getInvite() : null;
+                if (invite != null && workgroupJID.equals(invite.getFrom())) {
+                    String sessionID = null;
+                    Map<String, List<String>> metaData = null;
+
+                    pe = msg.getExtension(SessionID.ELEMENT_NAME,
+                            SessionID.NAMESPACE);
+                    if (pe != null) {
+                        sessionID = ((SessionID)pe).getSessionID();
+                    }
+
+                    pe = msg.getExtension(MetaData.ELEMENT_NAME,
+                            MetaData.NAMESPACE);
+                    if (pe != null) {
+                        metaData = ((MetaData)pe).getMetaData();
+                    }
+
+                    WorkgroupInvitation inv = new WorkgroupInvitation(connection.getUser(), msg.getFrom(),
+                            workgroupJID, sessionID, msg.getBody(),
+                            msg.getFrom(), metaData);
+
+                    fireInvitationEvent(inv);
+                }
+            }
+        }
+    }
+
+    /**
+     * IQ packet to request joining the workgroup queue.
+     */
+    private class JoinQueuePacket extends IQ {
+
+        private String userID = null;
+        private DataForm form;
+
+        public JoinQueuePacket(String workgroup, Form answerForm, String userID) {
+            this.userID = userID;
+
+            setTo(workgroup);
+            setType(IQ.Type.SET);
+
+            form = answerForm.getDataFormToSend();
+            addExtension(form);
+        }
+
+        public String getChildElementXML() {
+            StringBuilder buf = new StringBuilder();
+
+            buf.append("<join-queue xmlns=\"http://jabber.org/protocol/workgroup\">");
+            buf.append("<queue-notifications/>");
+            // Add the user unique identification if the session is anonymous
+            if (connection.isAnonymous()) {
+                buf.append(new UserID(userID).toXML());
+            }
+
+            // Append data form text
+            buf.append(form.toXML());
+
+            buf.append("</join-queue>");
+
+            return buf.toString();
+        }
+    }
+
+    /**
+     * Returns a single chat setting based on it's identified key.
+     *
+     * @param key the key to find.
+     * @return the ChatSetting if found, otherwise false.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public ChatSetting getChatSetting(String key) throws XMPPException {
+        ChatSettings chatSettings = getChatSettings(key, -1);
+        return chatSettings.getFirstEntry();
+    }
+
+    /**
+     * Returns ChatSettings based on type.
+     *
+     * @param type the type of ChatSettings to return.
+     * @return the ChatSettings of given type, otherwise null.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public ChatSettings getChatSettings(int type) throws XMPPException {
+        return getChatSettings(null, type);
+    }
+
+    /**
+     * Returns all ChatSettings.
+     *
+     * @return all ChatSettings of a given workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public ChatSettings getChatSettings() throws XMPPException {
+        return getChatSettings(null, -1);
+    }
+
+
+    /**
+     * Asks the workgroup for it's Chat Settings.
+     *
+     * @return key specify a key to retrieve only that settings. Otherwise for all settings, key should be null.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    private ChatSettings getChatSettings(String key, int type) throws XMPPException {
+        ChatSettings request = new ChatSettings();
+        if (key != null) {
+            request.setKey(key);
+        }
+        if (type != -1) {
+            request.setType(type);
+        }
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        ChatSettings response = (ChatSettings)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * The workgroup service may be configured to send email. This queries the Workgroup Service
+     * to see if the email service has been configured and is available.
+     *
+     * @return true if the email service is available, otherwise return false.
+     */
+    public boolean isEmailAvailable() {
+        ServiceDiscoveryManager discoManager = ServiceDiscoveryManager.getInstanceFor(connection);
+
+        try {
+            String workgroupService = StringUtils.parseServer(workgroupJID);
+            DiscoverInfo infoResult = discoManager.discoverInfo(workgroupService);
+            return infoResult.containsFeature("jive:email:provider");
+        }
+        catch (XMPPException e) {
+            return false;
+        }
+    }
+
+    /**
+     * Asks the workgroup for it's Offline Settings.
+     *
+     * @return offlineSettings the offline settings for this workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public OfflineSettings getOfflineSettings() throws XMPPException {
+        OfflineSettings request = new OfflineSettings();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        OfflineSettings response = (OfflineSettings)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Asks the workgroup for it's Sound Settings.
+     *
+     * @return soundSettings the sound settings for the specified workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public SoundSettings getSoundSettings() throws XMPPException {
+        SoundSettings request = new SoundSettings();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        SoundSettings response = (SoundSettings)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Asks the workgroup for it's Properties
+     *
+     * @return the WorkgroupProperties for the specified workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public WorkgroupProperties getWorkgroupProperties() throws XMPPException {
+        WorkgroupProperties request = new WorkgroupProperties();
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        WorkgroupProperties response = (WorkgroupProperties)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+    /**
+     * Asks the workgroup for it's Properties
+     *
+     * @param jid the jid of the user who's information you would like the workgroup to retreive.
+     * @return the WorkgroupProperties for the specified workgroup.
+     * @throws XMPPException if an error occurs while getting information from the server.
+     */
+    public WorkgroupProperties getWorkgroupProperties(String jid) throws XMPPException {
+        WorkgroupProperties request = new WorkgroupProperties();
+        request.setJid(jid);
+        request.setType(IQ.Type.GET);
+        request.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(request.getPacketID()));
+        connection.sendPacket(request);
+
+
+        WorkgroupProperties response = (WorkgroupProperties)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return response;
+    }
+
+
+    /**
+     * Returns the Form to use for all clients of a workgroup. It is unlikely that the server
+     * will change the form (without a restart) so it is safe to keep the returned form
+     * for future submissions.
+     *
+     * @return the Form to use for searching transcripts.
+     * @throws XMPPException if an error occurs while sending the request to the server.
+     */
+    public Form getWorkgroupForm() throws XMPPException {
+        WorkgroupForm workgroupForm = new WorkgroupForm();
+        workgroupForm.setType(IQ.Type.GET);
+        workgroupForm.setTo(workgroupJID);
+
+        PacketCollector collector = connection.createPacketCollector(new PacketIDFilter(workgroupForm.getPacketID()));
+        connection.sendPacket(workgroupForm);
+
+        WorkgroupForm response = (WorkgroupForm)collector.nextResult(SmackConfiguration.getPacketReplyTimeout());
+
+        // Cancel the collector.
+        collector.cancel();
+        if (response == null) {
+            throw new XMPPException("No response from server on status set.");
+        }
+        if (response.getError() != null) {
+            throw new XMPPException(response.getError());
+        }
+        return Form.getFormFrom(response);
+    }
+
+    /*
+    public static void main(String args[]) throws Exception {
+        Connection con = new XMPPConnection("anteros");
+        con.connect();
+        con.loginAnonymously();
+
+        Workgroup workgroup = new Workgroup("demo@workgroup.anteros", con);
+        WorkgroupProperties props = workgroup.getWorkgroupProperties("derek@anteros.com");
+
+        System.out.print(props);
+        con.disconnect();
+    }
+    */
+
+
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/util/ListenerEventDispatcher.java b/src/org/jivesoftware/smackx/workgroup/util/ListenerEventDispatcher.java
new file mode 100644
index 0000000..533b9a1
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/util/ListenerEventDispatcher.java
@@ -0,0 +1,132 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.util;
+
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.ListIterator;
+
+/**
+ * This class is a very flexible event dispatcher which implements Runnable so that it can
+ * dispatch easily from a newly created thread. The usage of this in code is more or less:
+ * create a new instance of this class, use addListenerTriplet to add as many listeners
+ * as desired to be messaged, create a new Thread using the instance of this class created
+ * as the argument to the constructor, start the new Thread instance.<p>
+ *
+ * Also, this is intended to be used to message methods that either return void, or have
+ * a return which the developer using this class is uninterested in receiving.
+ *
+ * @author loki der quaeler
+ */
+public class ListenerEventDispatcher
+    implements Runnable {
+
+    protected transient ArrayList<TripletContainer> triplets;
+
+    protected transient boolean hasFinishedDispatching;
+    protected transient boolean isRunning;
+
+    public ListenerEventDispatcher () {
+        super();
+
+        this.triplets = new ArrayList<TripletContainer>();
+
+        this.hasFinishedDispatching = false;
+        this.isRunning = false;
+    }
+
+    /**
+     * Add a listener triplet - the instance of the listener to be messaged, the Method on which
+     *  the listener should be messaged, and the Object array of arguments to be supplied to the
+     *  Method. No attempts are made to determine whether this triplet was already added.<br>
+     *
+     * Messages are dispatched in the order in which they're added via this method; so if triplet
+     *  X is added after triplet Z, then triplet Z will undergo messaging prior to triplet X.<br>
+     *
+     * This method should not be called once the owning Thread instance has been started; if it
+     *  is called, the triplet will not be added to the messaging queue.<br>
+     *
+     * @param listenerInstance the instance of the listener to receive the associated notification
+     * @param listenerMethod the Method instance representing the method through which notification
+     *                          will occur
+     * @param methodArguments the arguments supplied to the notification method
+     */
+    public void addListenerTriplet(Object listenerInstance, Method listenerMethod,
+            Object[] methodArguments)
+    {
+        if (!this.isRunning) {
+            this.triplets.add(new TripletContainer(listenerInstance, listenerMethod,
+                    methodArguments));
+        }
+    }
+
+    /**
+     * @return whether this instance has finished dispatching its messages
+     */
+    public boolean hasFinished() {
+        return this.hasFinishedDispatching;
+    }
+
+    public void run() {
+        ListIterator<TripletContainer> li = null;
+
+        this.isRunning = true;
+
+        li = this.triplets.listIterator();
+        while (li.hasNext()) {
+            TripletContainer tc = li.next();
+
+            try {
+                tc.getListenerMethod().invoke(tc.getListenerInstance(), tc.getMethodArguments());
+            } catch (Exception e) {
+                System.err.println("Exception dispatching an event: " + e);
+
+                e.printStackTrace();
+            }
+        }
+
+        this.hasFinishedDispatching = true;
+    }
+
+
+    protected class TripletContainer {
+
+        protected Object listenerInstance;
+        protected Method listenerMethod;
+        protected Object[] methodArguments;
+
+        protected TripletContainer (Object inst, Method meth, Object[] args) {
+            super();
+
+            this.listenerInstance = inst;
+            this.listenerMethod = meth;
+            this.methodArguments = args;
+        }
+
+        protected Object getListenerInstance() {
+            return this.listenerInstance;
+        }
+
+        protected Method getListenerMethod() {
+            return this.listenerMethod;
+        }
+
+        protected Object[] getMethodArguments() {
+            return this.methodArguments;
+        }
+    }
+}
\ No newline at end of file
diff --git a/src/org/jivesoftware/smackx/workgroup/util/MetaDataUtils.java b/src/org/jivesoftware/smackx/workgroup/util/MetaDataUtils.java
new file mode 100644
index 0000000..5be1c1a
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/util/MetaDataUtils.java
@@ -0,0 +1,103 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.util;
+
+import org.jivesoftware.smackx.workgroup.MetaData;
+import org.jivesoftware.smack.util.StringUtils;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+import java.io.IOException;
+import java.util.*;
+
+/**
+ * Utility class for meta-data parsing and writing.
+ *
+ * @author Matt Tucker
+ */
+public class MetaDataUtils {
+
+    /**
+     * Parses any available meta-data and returns it as a Map of String name/value pairs. The
+     * parser must be positioned at an opening meta-data tag, or the an empty map will be returned.
+     *
+     * @param parser the XML parser positioned at an opening meta-data tag.
+     * @return the meta-data.
+     * @throws XmlPullParserException if an error occurs while parsing the XML.
+     * @throws IOException            if an error occurs while parsing the XML.
+     */
+    public static Map<String, List<String>> parseMetaData(XmlPullParser parser) throws XmlPullParserException, IOException {
+        int eventType = parser.getEventType();
+
+        // If correctly positioned on an opening meta-data tag, parse meta-data.
+        if ((eventType == XmlPullParser.START_TAG)
+                && parser.getName().equals(MetaData.ELEMENT_NAME)
+                && parser.getNamespace().equals(MetaData.NAMESPACE)) {
+            Map<String, List<String>> metaData = new Hashtable<String, List<String>>();
+
+            eventType = parser.nextTag();
+
+            // Keep parsing until we've gotten to end of meta-data.
+            while ((eventType != XmlPullParser.END_TAG)
+                    || (!parser.getName().equals(MetaData.ELEMENT_NAME))) {
+                String name = parser.getAttributeValue(0);
+                String value = parser.nextText();
+
+                if (metaData.containsKey(name)) {
+                    List<String> values = metaData.get(name);
+                    values.add(value);
+                }
+                else {
+                    List<String> values = new ArrayList<String>();
+                    values.add(value);
+                    metaData.put(name, values);
+                }
+
+                eventType = parser.nextTag();
+            }
+
+            return metaData;
+        }
+
+        return Collections.emptyMap();
+    }
+
+    /**
+     * Serializes a Map of String name/value pairs into the meta-data XML format.
+     *
+     * @param metaData the Map of meta-data as Map&lt;String,List&lt;String>>
+     * @return the meta-data values in XML form.
+     */
+    public static String serializeMetaData(Map<String, List<String>> metaData) {
+        StringBuilder buf = new StringBuilder();
+        if (metaData != null && metaData.size() > 0) {
+            buf.append("<metadata xmlns=\"http://jivesoftware.com/protocol/workgroup\">");
+            for (Iterator<String> i = metaData.keySet().iterator(); i.hasNext();) {
+                String key = i.next();
+                List<String> value = metaData.get(key);
+                for (Iterator<String> it = value.iterator(); it.hasNext();) {
+                    String v = it.next();
+                    buf.append("<value name=\"").append(key).append("\">");
+                    buf.append(StringUtils.escapeForXML(v));
+                    buf.append("</value>");
+                }
+            }
+            buf.append("</metadata>");
+        }
+        return buf.toString();
+    }
+}
diff --git a/src/org/jivesoftware/smackx/workgroup/util/ModelUtil.java b/src/org/jivesoftware/smackx/workgroup/util/ModelUtil.java
new file mode 100644
index 0000000..0a4df15
--- /dev/null
+++ b/src/org/jivesoftware/smackx/workgroup/util/ModelUtil.java
@@ -0,0 +1,322 @@
+/**
+ * Copyright 2003-2007 Jive Software.
+ *
+ * All rights reserved. Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.jivesoftware.smackx.workgroup.util;
+
+import java.util.*;
+
+/**
+ * Utility methods frequently used by data classes and design-time
+ * classes.
+ */
+public final class ModelUtil {
+    private ModelUtil() {
+        //  Prevents instantiation.
+    }
+
+    /**
+     * This is a utility method that compares two objects when one or
+     * both of the objects might be <CODE>null</CODE>  The result of
+     * this method is determined as follows:
+     * <OL>
+     * <LI>If <CODE>o1</CODE> and <CODE>o2</CODE> are the same object
+     * according to the <CODE>==</CODE> operator, return
+     * <CODE>true</CODE>.
+     * <LI>Otherwise, if either <CODE>o1</CODE> or <CODE>o2</CODE> is
+     * <CODE>null</CODE>, return <CODE>false</CODE>.
+     * <LI>Otherwise, return <CODE>o1.equals(o2)</CODE>.
+     * </OL>
+     * <p/>
+     * This method produces the exact logically inverted result as the
+     * {@link #areDifferent(Object, Object)} method.<P>
+     * <p/>
+     * For array types, one of the <CODE>equals</CODE> methods in
+     * {@link java.util.Arrays} should be used instead of this method.
+     * Note that arrays with more than one dimension will require some
+     * custom code in order to implement <CODE>equals</CODE> properly.
+     */
+    public static final boolean areEqual(Object o1, Object o2) {
+        if (o1 == o2) {
+            return true;
+        }
+        else if (o1 == null || o2 == null) {
+            return false;
+        }
+        else {
+            return o1.equals(o2);
+        }
+    }
+
+    /**
+     * This is a utility method that compares two Booleans when one or
+     * both of the objects might be <CODE>null</CODE>  The result of
+     * this method is determined as follows:
+     * <OL>
+     * <LI>If <CODE>b1</CODE> and <CODE>b2</CODE> are both TRUE or
+     * neither <CODE>b1</CODE> nor <CODE>b2</CODE> is TRUE,
+     * return <CODE>true</CODE>.
+     * <LI>Otherwise, return <CODE>false</CODE>.
+     * </OL>
+     * <p/>
+     */
+    public static final boolean areBooleansEqual(Boolean b1, Boolean b2) {
+        // !jwetherb treat NULL the same as Boolean.FALSE
+        return (b1 == Boolean.TRUE && b2 == Boolean.TRUE) ||
+                (b1 != Boolean.TRUE && b2 != Boolean.TRUE);
+    }
+
+    /**
+     * This is a utility method that compares two objects when one or
+     * both of the objects might be <CODE>null</CODE>.  The result
+     * returned by this method is determined as follows:
+     * <OL>
+     * <LI>If <CODE>o1</CODE> and <CODE>o2</CODE> are the same object
+     * according to the <CODE>==</CODE> operator, return
+     * <CODE>false</CODE>.
+     * <LI>Otherwise, if either <CODE>o1</CODE> or <CODE>o2</CODE> is
+     * <CODE>null</CODE>, return <CODE>true</CODE>.
+     * <LI>Otherwise, return <CODE>!o1.equals(o2)</CODE>.
+     * </OL>
+     * <p/>
+     * This method produces the exact logically inverted result as the
+     * {@link #areEqual(Object, Object)} method.<P>
+     * <p/>
+     * For array types, one of the <CODE>equals</CODE> methods in
+     * {@link java.util.Arrays} should be used instead of this method.
+     * Note that arrays with more than one dimension will require some
+     * custom code in order to implement <CODE>equals</CODE> properly.
+     */
+    public static final boolean areDifferent(Object o1, Object o2) {
+        return !areEqual(o1, o2);
+    }
+
+
+    /**
+     * This is a utility method that compares two Booleans when one or
+     * both of the objects might be <CODE>null</CODE>  The result of
+     * this method is determined as follows:
+     * <OL>
+     * <LI>If <CODE>b1</CODE> and <CODE>b2</CODE> are both TRUE or
+     * neither <CODE>b1</CODE> nor <CODE>b2</CODE> is TRUE,
+     * return <CODE>false</CODE>.
+     * <LI>Otherwise, return <CODE>true</CODE>.
+     * </OL>
+     * <p/>
+     * This method produces the exact logically inverted result as the
+     * {@link #areBooleansEqual(Boolean, Boolean)} method.<P>
+     */
+    public static final boolean areBooleansDifferent(Boolean b1, Boolean b2) {
+        return !areBooleansEqual(b1, b2);
+    }
+
+
+    /**
+     * Returns <CODE>true</CODE> if the specified array is not null
+     * and contains a non-null element.  Returns <CODE>false</CODE>
+     * if the array is null or if all the array elements are null.
+     */
+    public static final boolean hasNonNullElement(Object[] array) {
+        if (array != null) {
+            final int n = array.length;
+            for (int i = 0; i < n; i++) {
+                if (array[i] != null) {
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Returns a single string that is the concatenation of all the
+     * strings in the specified string array.  A single space is
+     * put between each string array element.  Null array elements
+     * are skipped.  If the array itself is null, the empty string
+     * is returned.  This method is guaranteed to return a non-null
+     * value, if no expections are thrown.
+     */
+    public static final String concat(String[] strs) {
+        return concat(strs, " ");  //NOTRANS
+    }
+
+    /**
+     * Returns a single string that is the concatenation of all the
+     * strings in the specified string array.  The strings are separated
+     * by the specified delimiter.  Null array elements are skipped.  If
+     * the array itself is null, the empty string is returned.  This
+     * method is guaranteed to return a non-null value, if no expections
+     * are thrown.
+     */
+    public static final String concat(String[] strs, String delim) {
+        if (strs != null) {
+            final StringBuilder buf = new StringBuilder();
+            final int n = strs.length;
+            for (int i = 0; i < n; i++) {
+                final String str = strs[i];
+                if (str != null) {
+                    buf.append(str).append(delim);
+                }
+            }
+            final int length = buf.length();
+            if (length > 0) {
+                //  Trim trailing space.
+                buf.setLength(length - 1);
+            }
+            return buf.toString();
+        }
+        else {
+            return ""; // NOTRANS
+        }
+    }
+
+    /**
+     * Returns <CODE>true</CODE> if the specified {@link String} is not
+     * <CODE>null</CODE> and has a length greater than zero.  This is
+     * a very frequently occurring check.
+     */
+    public static final boolean hasLength(String s) {
+        return (s != null && s.length() > 0);
+    }
+
+
+    /**
+     * Returns <CODE>null</CODE> if the specified string is empty or
+     * <CODE>null</CODE>.  Otherwise the string itself is returned.
+     */
+    public static final String nullifyIfEmpty(String s) {
+        return ModelUtil.hasLength(s) ? s : null;
+    }
+
+    /**
+     * Returns <CODE>null</CODE> if the specified object is null
+     * or if its <CODE>toString()</CODE> representation is empty.
+     * Otherwise, the <CODE>toString()</CODE> representation of the
+     * object itself is returned.
+     */
+    public static final String nullifyingToString(Object o) {
+        return o != null ? nullifyIfEmpty(o.toString()) : null;
+    }
+
+    /**
+     * Determines if a string has been changed.
+     *
+     * @param oldString is the initial value of the String
+     * @param newString is the new value of the String
+     * @return true If both oldString and newString are null or if they are
+     *         both not null and equal to each other.  Otherwise returns false.
+     */
+    public static boolean hasStringChanged(String oldString, String newString) {
+        if (oldString == null && newString == null) {
+            return false;
+        }
+        else if ((oldString == null && newString != null)
+                || (oldString != null && newString == null)) {
+            return true;
+        }
+        else {
+            return !oldString.equals(newString);
+        }
+    }
+
+    public static String getTimeFromLong(long diff) {
+        final String HOURS = "h";
+        final String MINUTES = "min";
+        final String SECONDS = "sec";
+
+        final long MS_IN_A_DAY = 1000 * 60 * 60 * 24;
+        final long MS_IN_AN_HOUR = 1000 * 60 * 60;
+        final long MS_IN_A_MINUTE = 1000 * 60;
+        final long MS_IN_A_SECOND = 1000;
+        diff = diff % MS_IN_A_DAY;
+        long numHours = diff / MS_IN_AN_HOUR;
+        diff = diff % MS_IN_AN_HOUR;
+        long numMinutes = diff / MS_IN_A_MINUTE;
+        diff = diff % MS_IN_A_MINUTE;
+        long numSeconds = diff / MS_IN_A_SECOND;
+        diff = diff % MS_IN_A_SECOND;
+
+        StringBuilder buf = new StringBuilder();
+        if (numHours > 0) {
+            buf.append(numHours + " " + HOURS + ", ");
+        }
+
+        if (numMinutes > 0) {
+            buf.append(numMinutes + " " + MINUTES + ", ");
+        }
+
+        buf.append(numSeconds + " " + SECONDS);
+
+        String result = buf.toString();
+        return result;
+    }
+
+
+    /**
+     * Build a List of all elements in an Iterator.
+     */
+    public static <T> List<T> iteratorAsList(Iterator<T> i) {
+        ArrayList<T> list = new ArrayList<T>(10);
+        while (i.hasNext()) {
+            list.add(i.next());
+        }
+        return list;
+    }
+
+    /**
+     * Creates an Iterator that is the reverse of a ListIterator.
+     */
+    public static <T> Iterator<T> reverseListIterator(ListIterator<T> i) {
+        return new ReverseListIterator<T>(i);
+    }
+}
+
+/**
+ * An Iterator that is the reverse of a ListIterator.
+ */
+class ReverseListIterator<T> implements Iterator<T> {
+    private ListIterator<T> _i;
+
+    ReverseListIterator(ListIterator<T> i) {
+        _i = i;
+        while (_i.hasNext())
+            _i.next();
+    }
+
+    public boolean hasNext() {
+        return _i.hasPrevious();
+    }
+
+    public T next() {
+        return _i.previous();
+    }
+
+    public void remove() {
+        _i.remove();
+    }
+
+}
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/org/xbill/DNS/A6Record.java b/src/org/xbill/DNS/A6Record.java
new file mode 100644
index 0000000..a1c613a
--- /dev/null
+++ b/src/org/xbill/DNS/A6Record.java
@@ -0,0 +1,127 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+
+/**
+ * A6 Record - maps a domain name to an IPv6 address (experimental)
+ *
+ * @author Brian Wellington
+ */
+
+public class A6Record extends Record {
+
+private static final long serialVersionUID = -8815026887337346789L;
+
+private int prefixBits;
+private InetAddress suffix;
+private Name prefix;
+
+A6Record() {}
+
+Record
+getObject() {
+	return new A6Record();
+}
+
+/**
+ * Creates an A6 Record from the given data
+ * @param prefixBits The number of bits in the address prefix
+ * @param suffix The address suffix
+ * @param prefix The name of the prefix
+ */
+public
+A6Record(Name name, int dclass, long ttl, int prefixBits,
+	 InetAddress suffix, Name prefix)
+{
+	super(name, Type.A6, dclass, ttl);
+	this.prefixBits = checkU8("prefixBits", prefixBits);
+	if (suffix != null && Address.familyOf(suffix) != Address.IPv6)
+		throw new IllegalArgumentException("invalid IPv6 address");
+	this.suffix = suffix;
+	if (prefix != null)
+		this.prefix = checkName("prefix", prefix);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	prefixBits = in.readU8();
+	int suffixbits = 128 - prefixBits;
+	int suffixbytes = (suffixbits + 7) / 8;
+	if (prefixBits < 128) {
+		byte [] bytes = new byte[16];
+		in.readByteArray(bytes, 16 - suffixbytes, suffixbytes);
+		suffix = InetAddress.getByAddress(bytes);
+	}
+	if (prefixBits > 0)
+		prefix = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	prefixBits = st.getUInt8();
+	if (prefixBits > 128) {
+		throw st.exception("prefix bits must be [0..128]");
+	} else if (prefixBits < 128) {
+		String s = st.getString();
+		try {
+			suffix = Address.getByAddress(s, Address.IPv6);
+		}
+		catch (UnknownHostException e) {
+			throw st.exception("invalid IPv6 address: " + s);
+		}
+	}
+	if (prefixBits > 0)
+		prefix = st.getName(origin);
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(prefixBits);
+	if (suffix != null) {
+		sb.append(" ");
+		sb.append(suffix.getHostAddress());
+	}
+	if (prefix != null) {
+		sb.append(" ");
+		sb.append(prefix);
+	}
+	return sb.toString();
+}
+
+/** Returns the number of bits in the prefix */
+public int
+getPrefixBits() {
+	return prefixBits;
+}
+
+/** Returns the address suffix */
+public InetAddress
+getSuffix() {
+	return suffix;
+}
+
+/** Returns the address prefix */
+public Name
+getPrefix() {
+	return prefix;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(prefixBits);
+	if (suffix != null) {
+		int suffixbits = 128 - prefixBits;
+		int suffixbytes = (suffixbits + 7) / 8;
+		byte [] data = suffix.getAddress();
+		out.writeByteArray(data, 16 - suffixbytes, suffixbytes);
+	}
+	if (prefix != null)
+		prefix.toWire(out, null, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/AAAARecord.java b/src/org/xbill/DNS/AAAARecord.java
new file mode 100644
index 0000000..4b637aa
--- /dev/null
+++ b/src/org/xbill/DNS/AAAARecord.java
@@ -0,0 +1,67 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+
+/**
+ * IPv6 Address Record - maps a domain name to an IPv6 address
+ *
+ * @author Brian Wellington
+ */
+
+public class AAAARecord extends Record {
+
+private static final long serialVersionUID = -4588601512069748050L;
+
+private InetAddress address;
+
+AAAARecord() {}
+
+Record
+getObject() {
+	return new AAAARecord();
+}
+
+/**
+ * Creates an AAAA Record from the given data
+ * @param address The address suffix
+ */
+public
+AAAARecord(Name name, int dclass, long ttl, InetAddress address) {
+	super(name, Type.AAAA, dclass, ttl);
+	if (Address.familyOf(address) != Address.IPv6)
+		throw new IllegalArgumentException("invalid IPv6 address");
+	this.address = address;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	address = InetAddress.getByAddress(name.toString(),
+					   in.readByteArray(16));
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	address = st.getAddress(Address.IPv6);
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	return address.getHostAddress();
+}
+
+/** Returns the address */
+public InetAddress
+getAddress() {
+	return address;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(address.getAddress());
+}
+
+}
diff --git a/src/org/xbill/DNS/AFSDBRecord.java b/src/org/xbill/DNS/AFSDBRecord.java
new file mode 100644
index 0000000..4814faa
--- /dev/null
+++ b/src/org/xbill/DNS/AFSDBRecord.java
@@ -0,0 +1,46 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * AFS Data Base Record - maps a domain name to the name of an AFS cell
+ * database server.
+ *
+ *
+ * @author Brian Wellington
+ */
+
+public class AFSDBRecord extends U16NameBase {
+
+private static final long serialVersionUID = 3034379930729102437L;
+
+AFSDBRecord() {}
+
+Record
+getObject() {
+	return new AFSDBRecord();
+}
+
+/**
+ * Creates an AFSDB Record from the given data.
+ * @param subtype Indicates the type of service provided by the host.
+ * @param host The host providing the service.
+ */
+public
+AFSDBRecord(Name name, int dclass, long ttl, int subtype, Name host) {
+	super(name, Type.AFSDB, dclass, ttl, subtype, "subtype", host, "host");
+}
+
+/** Gets the subtype indicating the service provided by the host. */
+public int
+getSubtype() {
+	return getU16Field();
+}
+
+/** Gets the host providing service for the domain. */
+public Name
+getHost() {
+	return getNameField();
+}
+
+}
diff --git a/src/org/xbill/DNS/APLRecord.java b/src/org/xbill/DNS/APLRecord.java
new file mode 100644
index 0000000..5940da2
--- /dev/null
+++ b/src/org/xbill/DNS/APLRecord.java
@@ -0,0 +1,287 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * APL - Address Prefix List.  See RFC 3123.
+ *
+ * @author Brian Wellington
+ */
+
+/*
+ * Note: this currently uses the same constants as the Address class;
+ * this could change if more constants are defined for APL records.
+ */
+
+public class APLRecord extends Record {
+
+public static class Element {
+	public final int family;
+	public final boolean negative;
+	public final int prefixLength;
+	public final Object address;
+
+	private
+	Element(int family, boolean negative, Object address, int prefixLength)
+	{
+		this.family = family;
+		this.negative = negative;
+		this.address = address;
+		this.prefixLength = prefixLength;
+		if (!validatePrefixLength(family, prefixLength)) {
+			throw new IllegalArgumentException("invalid prefix " +
+							   "length");
+		}
+	}
+
+	/**
+	 * Creates an APL element corresponding to an IPv4 or IPv6 prefix.
+	 * @param negative Indicates if this prefix is a negation.
+	 * @param address The IPv4 or IPv6 address.
+	 * @param prefixLength The length of this prefix, in bits.
+	 * @throws IllegalArgumentException The prefix length is invalid.
+	 */
+	public
+	Element(boolean negative, InetAddress address, int prefixLength) {
+		this(Address.familyOf(address), negative, address,
+		     prefixLength);
+	}
+
+	public String
+	toString() {
+		StringBuffer sb = new StringBuffer();
+		if (negative)
+			sb.append("!");
+		sb.append(family);
+		sb.append(":");
+		if (family == Address.IPv4 || family == Address.IPv6)
+			sb.append(((InetAddress) address).getHostAddress());
+		else
+			sb.append(base16.toString((byte []) address));
+		sb.append("/");
+		sb.append(prefixLength);
+		return sb.toString();
+	}
+
+	public boolean
+	equals(Object arg) {
+		if (arg == null || !(arg instanceof Element))
+			return false;
+		Element elt = (Element) arg;
+		return (family == elt.family &&
+			negative == elt.negative &&
+			prefixLength == elt.prefixLength &&
+			address.equals(elt.address));
+	}
+
+	public int
+	hashCode() {
+		return address.hashCode() + prefixLength + (negative ? 1 : 0);
+	}
+}
+
+private static final long serialVersionUID = -1348173791712935864L;
+
+private List elements;
+
+APLRecord() {} 
+
+Record
+getObject() {
+	return new APLRecord();
+}
+
+private static boolean
+validatePrefixLength(int family, int prefixLength) {
+	if (prefixLength < 0 || prefixLength >= 256)
+		return false;
+	if ((family == Address.IPv4 && prefixLength > 32) ||
+	    (family == Address.IPv6 && prefixLength > 128))
+		return false;
+	return true;
+}
+
+/**
+ * Creates an APL Record from the given data.
+ * @param elements The list of APL elements.
+ */
+public
+APLRecord(Name name, int dclass, long ttl, List elements) {
+	super(name, Type.APL, dclass, ttl);
+	this.elements = new ArrayList(elements.size());
+	for (Iterator it = elements.iterator(); it.hasNext(); ) {
+		Object o = it.next();
+		if (!(o instanceof Element)) {
+			throw new IllegalArgumentException("illegal element");
+		}
+		Element element = (Element) o;
+		if (element.family != Address.IPv4 &&
+		    element.family != Address.IPv6)
+		{
+			throw new IllegalArgumentException("unknown family");
+		}
+		this.elements.add(element);
+
+	}
+}
+
+private static byte []
+parseAddress(byte [] in, int length) throws WireParseException {
+	if (in.length > length)
+		throw new WireParseException("invalid address length");
+	if (in.length == length)
+		return in;
+	byte [] out = new byte[length];
+	System.arraycopy(in, 0, out, 0, in.length);
+	return out;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	elements = new ArrayList(1);
+	while (in.remaining() != 0) {
+		int family = in.readU16();
+		int prefix = in.readU8();
+		int length = in.readU8();
+		boolean negative = (length & 0x80) != 0;
+		length &= ~0x80;
+
+		byte [] data = in.readByteArray(length);
+		Element element;
+		if (!validatePrefixLength(family, prefix)) {
+			throw new WireParseException("invalid prefix length");
+		}
+
+		if (family == Address.IPv4 || family == Address.IPv6) {
+			data = parseAddress(data,
+					    Address.addressLength(family));
+			InetAddress addr = InetAddress.getByAddress(data);
+			element = new Element(negative, addr, prefix);
+		} else {
+			element = new Element(family, negative, data, prefix);
+		}
+		elements.add(element);
+
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	elements = new ArrayList(1);
+	while (true) {
+		Tokenizer.Token t = st.get();
+		if (!t.isString())
+			break;
+
+		boolean negative = false;
+		int family = 0;
+		int prefix = 0;
+
+		String s = t.value;
+		int start = 0;
+		if (s.startsWith("!")) {
+			negative = true;
+			start = 1;
+		}
+		int colon = s.indexOf(':', start);
+		if (colon < 0)
+			throw st.exception("invalid address prefix element");
+		int slash = s.indexOf('/', colon);
+		if (slash < 0)
+			throw st.exception("invalid address prefix element");
+
+		String familyString = s.substring(start, colon);
+		String addressString = s.substring(colon + 1, slash);
+		String prefixString = s.substring(slash + 1);
+
+		try {
+			family = Integer.parseInt(familyString);
+		}
+		catch (NumberFormatException e) {
+			throw st.exception("invalid family");
+		}
+		if (family != Address.IPv4 && family != Address.IPv6)
+			throw st.exception("unknown family");
+
+		try {
+			prefix = Integer.parseInt(prefixString);
+		}
+		catch (NumberFormatException e) {
+			throw st.exception("invalid prefix length");
+		}
+
+		if (!validatePrefixLength(family, prefix)) {
+			throw st.exception("invalid prefix length");
+		}
+
+		byte [] bytes = Address.toByteArray(addressString, family);
+		if (bytes == null)
+			throw st.exception("invalid IP address " +
+					   addressString);
+
+		InetAddress address = InetAddress.getByAddress(bytes);
+		elements.add(new Element(negative, address, prefix));
+	}
+	st.unget();
+}
+
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	for (Iterator it = elements.iterator(); it.hasNext(); ) {
+		Element element = (Element) it.next();
+		sb.append(element);
+		if (it.hasNext())
+			sb.append(" ");
+	}
+	return sb.toString();
+}
+
+/** Returns the list of APL elements. */
+public List
+getElements() {
+	return elements;
+}
+
+private static int
+addressLength(byte [] addr) {
+	for (int i = addr.length - 1; i >= 0; i--) {
+		if (addr[i] != 0)
+			return i + 1;
+	}
+	return 0;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	for (Iterator it = elements.iterator(); it.hasNext(); ) {
+		Element element = (Element) it.next();
+		int length = 0;
+		byte [] data;
+		if (element.family == Address.IPv4 ||
+		    element.family == Address.IPv6)
+		{
+			InetAddress addr = (InetAddress) element.address;
+			data = addr.getAddress();
+			length = addressLength(data);
+		} else {
+			data = (byte []) element.address;
+			length = data.length;
+		}
+		int wlength = length;
+		if (element.negative) {
+			wlength |= 0x80;
+		}
+		out.writeU16(element.family);
+		out.writeU8(element.prefixLength);
+		out.writeU8(wlength);
+		out.writeByteArray(data, 0, length);
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/ARecord.java b/src/org/xbill/DNS/ARecord.java
new file mode 100644
index 0000000..4e13aa7
--- /dev/null
+++ b/src/org/xbill/DNS/ARecord.java
@@ -0,0 +1,90 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.net.*;
+import java.io.*;
+
+/**
+ * Address Record - maps a domain name to an Internet address
+ *
+ * @author Brian Wellington
+ */
+
+public class ARecord extends Record {
+
+private static final long serialVersionUID = -2172609200849142323L;
+
+private int addr;
+
+ARecord() {}
+
+Record
+getObject() {
+	return new ARecord();
+}
+
+private static final int
+fromArray(byte [] array) {
+	return (((array[0] & 0xFF) << 24) |
+		((array[1] & 0xFF) << 16) |
+		((array[2] & 0xFF) << 8) |
+		(array[3] & 0xFF));
+}
+
+private static final byte []
+toArray(int addr) {
+	byte [] bytes = new byte[4];
+	bytes[0] = (byte) ((addr >>> 24) & 0xFF);
+	bytes[1] = (byte) ((addr >>> 16) & 0xFF);
+	bytes[2] = (byte) ((addr >>> 8) & 0xFF);
+	bytes[3] = (byte) (addr & 0xFF);
+	return bytes;
+}
+
+/**
+ * Creates an A Record from the given data
+ * @param address The address that the name refers to
+ */
+public
+ARecord(Name name, int dclass, long ttl, InetAddress address) {
+	super(name, Type.A, dclass, ttl);
+	if (Address.familyOf(address) != Address.IPv4)
+		throw new IllegalArgumentException("invalid IPv4 address");
+	addr = fromArray(address.getAddress());
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	addr = fromArray(in.readByteArray(4));
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	InetAddress address = st.getAddress(Address.IPv4);
+	addr = fromArray(address.getAddress());
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	return (Address.toDottedQuad(toArray(addr)));
+}
+
+/** Returns the Internet address */
+public InetAddress
+getAddress() {
+	try {
+		return InetAddress.getByAddress(name.toString(),
+						toArray(addr));
+	} catch (UnknownHostException e) {
+		return null;
+	}
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU32(((long)addr) & 0xFFFFFFFFL);
+}
+
+}
diff --git a/src/org/xbill/DNS/Address.java b/src/org/xbill/DNS/Address.java
new file mode 100644
index 0000000..799185b
--- /dev/null
+++ b/src/org/xbill/DNS/Address.java
@@ -0,0 +1,402 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.net.*;
+import java.net.Inet6Address;
+
+/**
+ * Routines dealing with IP addresses.  Includes functions similar to
+ * those in the java.net.InetAddress class.
+ *
+ * @author Brian Wellington
+ */
+
+public final class Address {
+
+public static final int IPv4 = 1;
+public static final int IPv6 = 2;
+
+private
+Address() {}
+
+private static byte []
+parseV4(String s) {
+	int numDigits;
+	int currentOctet;
+	byte [] values = new byte[4];
+	int currentValue;
+	int length = s.length();
+
+	currentOctet = 0;
+	currentValue = 0;
+	numDigits = 0;
+	for (int i = 0; i < length; i++) {
+		char c = s.charAt(i);
+		if (c >= '0' && c <= '9') {
+			/* Can't have more than 3 digits per octet. */
+			if (numDigits == 3)
+				return null;
+			/* Octets shouldn't start with 0, unless they are 0. */
+			if (numDigits > 0 && currentValue == 0)
+				return null;
+			numDigits++;
+			currentValue *= 10;
+			currentValue += (c - '0');
+			/* 255 is the maximum value for an octet. */
+			if (currentValue > 255)
+				return null;
+		} else if (c == '.') {
+			/* Can't have more than 3 dots. */
+			if (currentOctet == 3)
+				return null;
+			/* Two consecutive dots are bad. */
+			if (numDigits == 0)
+				return null;
+			values[currentOctet++] = (byte) currentValue;
+			currentValue = 0;
+			numDigits = 0;
+		} else
+			return null;
+	}
+	/* Must have 4 octets. */
+	if (currentOctet != 3)
+		return null;
+	/* The fourth octet can't be empty. */
+	if (numDigits == 0)
+		return null;
+	values[currentOctet] = (byte) currentValue;
+	return values;
+}
+
+private static byte []
+parseV6(String s) {
+	int range = -1;
+	byte [] data = new byte[16];
+
+	String [] tokens = s.split(":", -1);
+
+	int first = 0;
+	int last = tokens.length - 1;
+
+	if (tokens[0].length() == 0) {
+		// If the first two tokens are empty, it means the string
+		// started with ::, which is fine.  If only the first is
+		// empty, the string started with :, which is bad.
+		if (last - first > 0 && tokens[1].length() == 0)
+			first++;
+		else
+			return null;
+	}
+
+	if (tokens[last].length() == 0) {
+		// If the last two tokens are empty, it means the string
+		// ended with ::, which is fine.  If only the last is
+		// empty, the string ended with :, which is bad.
+		if (last - first > 0 && tokens[last - 1].length() == 0)
+			last--;
+		else
+			return null;
+	}
+
+	if (last - first + 1 > 8)
+		return null;
+
+	int i, j;
+	for (i = first, j = 0; i <= last; i++) {
+		if (tokens[i].length() == 0) {
+			if (range >= 0)
+				return null;
+			range = j;
+			continue;
+		}
+
+		if (tokens[i].indexOf('.') >= 0) {
+			// An IPv4 address must be the last component
+			if (i < last)
+				return null;
+			// There can't have been more than 6 components.
+			if (i > 6)
+				return null;
+			byte [] v4addr = Address.toByteArray(tokens[i], IPv4);
+			if (v4addr == null)
+				return null;
+			for (int k = 0; k < 4; k++)
+				data[j++] = v4addr[k];
+			break;
+		}
+
+		try {
+			for (int k = 0; k < tokens[i].length(); k++) {
+				char c = tokens[i].charAt(k);
+				if (Character.digit(c, 16) < 0)
+					return null;
+			}
+			int x = Integer.parseInt(tokens[i], 16);
+			if (x > 0xFFFF || x < 0)
+				return null;
+			data[j++] = (byte)(x >>> 8);
+			data[j++] = (byte)(x & 0xFF);
+		}
+		catch (NumberFormatException e) {
+			return null;
+		}
+	}
+
+	if (j < 16 && range < 0)
+		return null;
+
+	if (range >= 0) {
+		int empty = 16 - j;
+		System.arraycopy(data, range, data, range + empty, j - range);
+		for (i = range; i < range + empty; i++)
+			data[i] = 0;
+	}
+
+	return data;
+}
+
+/**
+ * Convert a string containing an IP address to an array of 4 or 16 integers.
+ * @param s The address, in text format.
+ * @param family The address family.
+ * @return The address
+ */
+public static int []
+toArray(String s, int family) {
+	byte [] byteArray = toByteArray(s, family);
+	if (byteArray == null)
+		return null;
+	int [] intArray = new int[byteArray.length];
+	for (int i = 0; i < byteArray.length; i++)
+		intArray[i] = byteArray[i] & 0xFF;
+	return intArray;
+}
+
+/**
+ * Convert a string containing an IPv4 address to an array of 4 integers.
+ * @param s The address, in text format.
+ * @return The address
+ */
+public static int []
+toArray(String s) {
+	return toArray(s, IPv4);
+}
+
+/**
+ * Convert a string containing an IP address to an array of 4 or 16 bytes.
+ * @param s The address, in text format.
+ * @param family The address family.
+ * @return The address
+ */
+public static byte []
+toByteArray(String s, int family) {
+	if (family == IPv4)
+		return parseV4(s);
+	else if (family == IPv6)
+		return parseV6(s);
+	else
+		throw new IllegalArgumentException("unknown address family");
+}
+
+/**
+ * Determines if a string contains a valid IP address.
+ * @param s The string
+ * @return Whether the string contains a valid IP address
+ */
+public static boolean
+isDottedQuad(String s) {
+	byte [] address = Address.toByteArray(s, IPv4);
+	return (address != null);
+}
+
+/**
+ * Converts a byte array containing an IPv4 address into a dotted quad string.
+ * @param addr The array
+ * @return The string representation
+ */
+public static String
+toDottedQuad(byte [] addr) {
+	return ((addr[0] & 0xFF) + "." + (addr[1] & 0xFF) + "." +
+		(addr[2] & 0xFF) + "." + (addr[3] & 0xFF));
+}
+
+/**
+ * Converts an int array containing an IPv4 address into a dotted quad string.
+ * @param addr The array
+ * @return The string representation
+ */
+public static String
+toDottedQuad(int [] addr) {
+	return (addr[0] + "." + addr[1] + "." + addr[2] + "." + addr[3]);
+}
+
+private static Record []
+lookupHostName(String name) throws UnknownHostException {
+	try {
+		Record [] records = new Lookup(name).run();
+		if (records == null)
+			throw new UnknownHostException("unknown host");
+		return records;
+	}
+	catch (TextParseException e) {
+		throw new UnknownHostException("invalid name");
+	}
+}
+
+private static InetAddress
+addrFromRecord(String name, Record r) throws UnknownHostException {
+	ARecord a = (ARecord) r;
+	return InetAddress.getByAddress(name, a.getAddress().getAddress());
+}
+
+/**
+ * Determines the IP address of a host
+ * @param name The hostname to look up
+ * @return The first matching IP address
+ * @exception UnknownHostException The hostname does not have any addresses
+ */
+public static InetAddress
+getByName(String name) throws UnknownHostException {
+	try {
+		return getByAddress(name);
+	} catch (UnknownHostException e) {
+		Record [] records = lookupHostName(name);
+		return addrFromRecord(name, records[0]);
+	}
+}
+
+/**
+ * Determines all IP address of a host
+ * @param name The hostname to look up
+ * @return All matching IP addresses
+ * @exception UnknownHostException The hostname does not have any addresses
+ */
+public static InetAddress []
+getAllByName(String name) throws UnknownHostException {
+	try {
+		InetAddress addr = getByAddress(name);
+		return new InetAddress[] {addr};
+	} catch (UnknownHostException e) {
+		Record [] records = lookupHostName(name);
+		InetAddress [] addrs = new InetAddress[records.length];
+		for (int i = 0; i < records.length; i++)
+			addrs[i] = addrFromRecord(name, records[i]);
+		return addrs;
+	}
+}
+
+/**
+ * Converts an address from its string representation to an IP address.
+ * The address can be either IPv4 or IPv6.
+ * @param addr The address, in string form
+ * @return The IP addresses
+ * @exception UnknownHostException The address is not a valid IP address.
+ */
+public static InetAddress
+getByAddress(String addr) throws UnknownHostException {
+	byte [] bytes;
+	bytes = toByteArray(addr, IPv4);
+	if (bytes != null)
+		return InetAddress.getByAddress(addr, bytes);
+	bytes = toByteArray(addr, IPv6);
+	if (bytes != null)
+		return InetAddress.getByAddress(addr, bytes);
+	throw new UnknownHostException("Invalid address: " + addr);
+}
+
+/**
+ * Converts an address from its string representation to an IP address in
+ * a particular family.
+ * @param addr The address, in string form
+ * @param family The address family, either IPv4 or IPv6.
+ * @return The IP addresses
+ * @exception UnknownHostException The address is not a valid IP address in
+ * the specified address family.
+ */
+public static InetAddress
+getByAddress(String addr, int family) throws UnknownHostException {
+	if (family != IPv4 && family != IPv6)
+		throw new IllegalArgumentException("unknown address family");
+	byte [] bytes;
+	bytes = toByteArray(addr, family);
+	if (bytes != null)
+		return InetAddress.getByAddress(addr, bytes);
+	throw new UnknownHostException("Invalid address: " + addr);
+}
+
+/**
+ * Determines the hostname for an address
+ * @param addr The address to look up
+ * @return The associated host name
+ * @exception UnknownHostException There is no hostname for the address
+ */
+public static String
+getHostName(InetAddress addr) throws UnknownHostException {
+	Name name = ReverseMap.fromAddress(addr);
+	Record [] records = new Lookup(name, Type.PTR).run();
+	if (records == null)
+		throw new UnknownHostException("unknown address");
+	PTRRecord ptr = (PTRRecord) records[0];
+	return ptr.getTarget().toString();
+}
+
+/**
+ * Returns the family of an InetAddress.
+ * @param address The supplied address.
+ * @return The family, either IPv4 or IPv6.
+ */
+public static int
+familyOf(InetAddress address) {
+	if (address instanceof Inet4Address)
+		return IPv4;
+	if (address instanceof Inet6Address)
+		return IPv6;
+	throw new IllegalArgumentException("unknown address family");
+}
+
+/**
+ * Returns the length of an address in a particular family.
+ * @param family The address family, either IPv4 or IPv6.
+ * @return The length of addresses in that family.
+ */
+public static int
+addressLength(int family) {
+	if (family == IPv4)
+		return 4;
+	if (family == IPv6)
+		return 16;
+	throw new IllegalArgumentException("unknown address family");
+}
+
+/**
+ * Truncates an address to the specified number of bits.  For example,
+ * truncating the address 10.1.2.3 to 8 bits would yield 10.0.0.0.
+ * @param address The source address
+ * @param maskLength The number of bits to truncate the address to.
+ */
+public static InetAddress
+truncate(InetAddress address, int maskLength)
+{
+	int family = familyOf(address);
+	int maxMaskLength = addressLength(family) * 8;
+	if (maskLength < 0 || maskLength > maxMaskLength)
+		throw new IllegalArgumentException("invalid mask length");
+	if (maskLength == maxMaskLength)
+		return address;
+	byte [] bytes = address.getAddress();
+	for (int i = maskLength / 8 + 1; i < bytes.length; i++)
+		bytes[i] = 0;
+	int maskBits = maskLength % 8;
+	int bitmask = 0;
+	for (int i = 0; i < maskBits; i++)
+		bitmask |= (1 << (7 - i));
+	bytes[maskLength / 8] &= bitmask;
+	try {
+		return InetAddress.getByAddress(bytes);
+	} catch (UnknownHostException e) {
+		throw new IllegalArgumentException("invalid address");
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/CERTRecord.java b/src/org/xbill/DNS/CERTRecord.java
new file mode 100644
index 0000000..39bcef3
--- /dev/null
+++ b/src/org/xbill/DNS/CERTRecord.java
@@ -0,0 +1,224 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * Certificate Record  - Stores a certificate associated with a name.  The
+ * certificate might also be associated with a KEYRecord.
+ * @see KEYRecord
+ *
+ * @author Brian Wellington
+ */
+
+public class CERTRecord extends Record {
+
+public static class CertificateType {
+	/** Certificate type identifiers.  See RFC 4398 for more detail. */
+
+	private CertificateType() {}
+
+	/** PKIX (X.509v3) */
+	public static final int PKIX = 1;
+
+	/** Simple Public Key Infrastructure */
+	public static final int SPKI = 2;
+
+	/** Pretty Good Privacy */
+	public static final int PGP = 3;
+
+	/** URL of an X.509 data object */
+	public static final int IPKIX = 4;
+
+	/** URL of an SPKI certificate */
+	public static final int ISPKI = 5;
+
+	/** Fingerprint and URL of an OpenPGP packet */
+	public static final int IPGP = 6;
+
+	/** Attribute Certificate */
+	public static final int ACPKIX = 7;
+
+	/** URL of an Attribute Certificate */
+	public static final int IACPKIX = 8;
+
+	/** Certificate format defined by URI */
+	public static final int URI = 253;
+
+	/** Certificate format defined by OID */
+	public static final int OID = 254;
+
+	private static Mnemonic types = new Mnemonic("Certificate type",
+						     Mnemonic.CASE_UPPER);
+
+	static {
+		types.setMaximum(0xFFFF);
+		types.setNumericAllowed(true);
+
+		types.add(PKIX, "PKIX");
+		types.add(SPKI, "SPKI");
+		types.add(PGP, "PGP");
+		types.add(PKIX, "IPKIX");
+		types.add(SPKI, "ISPKI");
+		types.add(PGP, "IPGP");
+		types.add(PGP, "ACPKIX");
+		types.add(PGP, "IACPKIX");
+		types.add(URI, "URI");
+		types.add(OID, "OID");
+	}
+
+	/**
+	 * Converts a certificate type into its textual representation
+	 */
+	public static String
+	string(int type) {
+		return types.getText(type);
+	}
+
+	/**
+	 * Converts a textual representation of an certificate type into its
+	 * numeric code.  Integers in the range 0..65535 are also accepted.
+	 * @param s The textual representation of the algorithm
+	 * @return The algorithm code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return types.getValue(s);
+	}
+}
+
+/** PKIX (X.509v3) */
+public static final int PKIX = CertificateType.PKIX;
+
+/** Simple Public Key Infrastructure  */
+public static final int SPKI = CertificateType.SPKI;
+
+/** Pretty Good Privacy */
+public static final int PGP = CertificateType.PGP;
+
+/** Certificate format defined by URI */
+public static final int URI = CertificateType.URI;
+
+/** Certificate format defined by IOD */
+public static final int OID = CertificateType.OID;
+
+private static final long serialVersionUID = 4763014646517016835L;
+
+private int certType, keyTag;
+private int alg;
+private byte [] cert;
+
+CERTRecord() {}
+
+Record
+getObject() {
+	return new CERTRecord();
+}
+
+/**
+ * Creates a CERT Record from the given data
+ * @param certType The type of certificate (see constants)
+ * @param keyTag The ID of the associated KEYRecord, if present
+ * @param alg The algorithm of the associated KEYRecord, if present
+ * @param cert Binary data representing the certificate
+ */
+public
+CERTRecord(Name name, int dclass, long ttl, int certType, int keyTag,
+	   int alg, byte []  cert)
+{
+	super(name, Type.CERT, dclass, ttl);
+	this.certType = checkU16("certType", certType);
+	this.keyTag = checkU16("keyTag", keyTag);
+	this.alg = checkU8("alg", alg);
+	this.cert = cert;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	certType = in.readU16();
+	keyTag = in.readU16();
+	alg = in.readU8();
+	cert = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String certTypeString = st.getString();
+	certType = CertificateType.value(certTypeString);
+	if (certType < 0)
+		throw st.exception("Invalid certificate type: " +
+				   certTypeString);
+	keyTag = st.getUInt16();
+	String algString = st.getString();
+	alg = DNSSEC.Algorithm.value(algString);
+	if (alg < 0)
+		throw st.exception("Invalid algorithm: " + algString);
+	cert = st.getBase64();
+}
+
+/**
+ * Converts rdata to a String
+ */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append (certType);
+	sb.append (" ");
+	sb.append (keyTag);
+	sb.append (" ");
+	sb.append (alg);
+	if (cert != null) {
+		if (Options.check("multiline")) {
+			sb.append(" (\n");
+			sb.append(base64.formatString(cert, 64, "\t", true));
+		} else {
+			sb.append(" ");
+			sb.append(base64.toString(cert));
+		}
+	}
+	return sb.toString();
+}
+
+/**
+ * Returns the type of certificate
+ */
+public int
+getCertType() {
+	return certType;
+}
+
+/**
+ * Returns the ID of the associated KEYRecord, if present
+ */
+public int
+getKeyTag() {
+	return keyTag;
+}
+
+/**
+ * Returns the algorithm of the associated KEYRecord, if present
+ */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ * Returns the binary representation of the certificate
+ */
+public byte []
+getCert() {
+	return cert;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(certType);
+	out.writeU16(keyTag);
+	out.writeU8(alg);
+	out.writeByteArray(cert);
+}
+
+}
diff --git a/src/org/xbill/DNS/CNAMERecord.java b/src/org/xbill/DNS/CNAMERecord.java
new file mode 100644
index 0000000..8db9453
--- /dev/null
+++ b/src/org/xbill/DNS/CNAMERecord.java
@@ -0,0 +1,45 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * CNAME Record  - maps an alias to its real name
+ *
+ * @author Brian Wellington
+ */
+
+public class CNAMERecord extends SingleCompressedNameBase {
+
+private static final long serialVersionUID = -4020373886892538580L;
+
+CNAMERecord() {}
+
+Record
+getObject() {
+	return new CNAMERecord();
+}
+
+/**
+ * Creates a new CNAMERecord with the given data
+ * @param alias The name to which the CNAME alias points
+ */
+public
+CNAMERecord(Name name, int dclass, long ttl, Name alias) {
+	super(name, Type.CNAME, dclass, ttl, alias, "alias");
+}
+
+/**
+ * Gets the target of the CNAME Record
+ */
+public Name
+getTarget() {
+	return getSingleName();
+}
+
+/** Gets the alias specified by the CNAME Record */
+public Name
+getAlias() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/Cache.java b/src/org/xbill/DNS/Cache.java
new file mode 100644
index 0000000..5497f45
--- /dev/null
+++ b/src/org/xbill/DNS/Cache.java
@@ -0,0 +1,846 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A cache of DNS records.  The cache obeys TTLs, so items are purged after
+ * their validity period is complete.  Negative answers are cached, to
+ * avoid repeated failed DNS queries.  The credibility of each RRset is
+ * maintained, so that more credible records replace less credible records,
+ * and lookups can specify the minimum credibility of data they are requesting.
+ * @see RRset
+ * @see Credibility
+ *
+ * @author Brian Wellington
+ */
+
+public class Cache {
+
+private interface Element {
+	public boolean expired();
+	public int compareCredibility(int cred);
+	public int getType();
+}
+
+private static int
+limitExpire(long ttl, long maxttl) {
+	if (maxttl >= 0 && maxttl < ttl)
+		ttl = maxttl;
+	long expire = (System.currentTimeMillis() / 1000) + ttl;
+	if (expire < 0 || expire > Integer.MAX_VALUE)
+		return Integer.MAX_VALUE;
+	return (int)expire;
+}
+
+private static class CacheRRset extends RRset implements Element {
+	private static final long serialVersionUID = 5971755205903597024L;
+	
+	int credibility;
+	int expire;
+
+	public
+	CacheRRset(Record rec, int cred, long maxttl) {
+		super();
+		this.credibility = cred;
+		this.expire = limitExpire(rec.getTTL(), maxttl);
+		addRR(rec);
+	}
+
+	public
+	CacheRRset(RRset rrset, int cred, long maxttl) {
+		super(rrset);
+		this.credibility = cred;
+		this.expire = limitExpire(rrset.getTTL(), maxttl);
+	}
+
+	public final boolean
+	expired() {
+		int now = (int)(System.currentTimeMillis() / 1000);
+		return (now >= expire);
+	}
+
+	public final int
+	compareCredibility(int cred) {
+		return credibility - cred;
+	}
+
+	public String
+	toString() {
+		StringBuffer sb = new StringBuffer();
+		sb.append(super.toString());
+		sb.append(" cl = ");
+		sb.append(credibility);
+		return sb.toString();
+	}
+}
+
+private static class NegativeElement implements Element {
+	int type;
+	Name name;
+	int credibility;
+	int expire;
+
+	public
+	NegativeElement(Name name, int type, SOARecord soa, int cred,
+			long maxttl)
+	{
+		this.name = name;
+		this.type = type;
+		long cttl = 0;
+		if (soa != null)
+			cttl = soa.getMinimum();
+		this.credibility = cred;
+		this.expire = limitExpire(cttl, maxttl);
+	}
+
+	public int
+	getType() {
+		return type;
+	}
+
+	public final boolean
+	expired() {
+		int now = (int)(System.currentTimeMillis() / 1000);
+		return (now >= expire);
+	}
+
+	public final int
+	compareCredibility(int cred) {
+		return credibility - cred;
+	}
+
+	public String
+	toString() {
+		StringBuffer sb = new StringBuffer();
+		if (type == 0)
+			sb.append("NXDOMAIN " + name);
+		else
+			sb.append("NXRRSET " + name + " " + Type.string(type));
+		sb.append(" cl = ");
+		sb.append(credibility);
+		return sb.toString();
+	}
+}
+
+private static class CacheMap extends LinkedHashMap {
+	private int maxsize = -1;
+
+	CacheMap(int maxsize) {
+		super(16, (float) 0.75, true);
+		this.maxsize = maxsize;
+	}
+
+	int
+	getMaxSize() {
+		return maxsize;
+	}
+
+	void
+	setMaxSize(int maxsize) {
+		/*
+		 * Note that this doesn't shrink the size of the map if
+		 * the maximum size is lowered, but it should shrink as
+		 * entries expire.
+		 */
+		this.maxsize = maxsize;
+	}
+
+	protected boolean removeEldestEntry(Map.Entry eldest) {
+		return maxsize >= 0 && size() > maxsize;
+	}
+}
+
+private CacheMap data;
+private int maxncache = -1;
+private int maxcache = -1;
+private int dclass;
+
+private static final int defaultMaxEntries = 50000;
+
+/**
+ * Creates an empty Cache
+ *
+ * @param dclass The DNS class of this cache
+ * @see DClass
+ */
+public
+Cache(int dclass) {
+	this.dclass = dclass;
+	data = new CacheMap(defaultMaxEntries);
+}
+
+/**
+ * Creates an empty Cache for class IN.
+ * @see DClass
+ */
+public
+Cache() {
+	this(DClass.IN);
+}
+
+/**
+ * Creates a Cache which initially contains all records in the specified file.
+ */
+public
+Cache(String file) throws IOException {
+	data = new CacheMap(defaultMaxEntries);
+	Master m = new Master(file);
+	Record record;
+	while ((record = m.nextRecord()) != null)
+		addRecord(record, Credibility.HINT, m);
+}
+
+private synchronized Object
+exactName(Name name) {
+	return data.get(name);
+}
+
+private synchronized void
+removeName(Name name) {
+	data.remove(name);
+}
+
+private synchronized Element []
+allElements(Object types) {
+	if (types instanceof List) {
+		List typelist = (List) types;
+		int size = typelist.size();
+		return (Element []) typelist.toArray(new Element[size]);
+	} else {
+		Element set = (Element) types;
+		return new Element[] {set};
+	}
+}
+
+private synchronized Element
+oneElement(Name name, Object types, int type, int minCred) {
+	Element found = null;
+
+	if (type == Type.ANY)
+		throw new IllegalArgumentException("oneElement(ANY)");
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			Element set = (Element) list.get(i);
+			if (set.getType() == type) {
+				found = set;
+				break;
+			}
+		}
+	} else {
+		Element set = (Element) types;
+		if (set.getType() == type)
+			found = set;
+	}
+	if (found == null)
+		return null;
+	if (found.expired()) {
+		removeElement(name, type);
+		return null;
+	}
+	if (found.compareCredibility(minCred) < 0)
+		return null;
+	return found;
+}
+
+private synchronized Element
+findElement(Name name, int type, int minCred) {
+	Object types = exactName(name);
+	if (types == null)
+		return null;
+	return oneElement(name, types, type, minCred);
+}
+
+private synchronized void
+addElement(Name name, Element element) {
+	Object types = data.get(name);
+	if (types == null) {
+		data.put(name, element);
+		return;
+	}
+	int type = element.getType();
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			Element elt = (Element) list.get(i);
+			if (elt.getType() == type) {
+				list.set(i, element);
+				return;
+			}
+		}
+		list.add(element);
+	} else {
+		Element elt = (Element) types;
+		if (elt.getType() == type)
+			data.put(name, element);
+		else {
+			LinkedList list = new LinkedList();
+			list.add(elt);
+			list.add(element);
+			data.put(name, list);
+		}
+	}
+}
+
+private synchronized void
+removeElement(Name name, int type) {
+	Object types = data.get(name);
+	if (types == null) {
+		return;
+	}
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			Element elt = (Element) list.get(i);
+			if (elt.getType() == type) {
+				list.remove(i);
+				if (list.size() == 0)
+					data.remove(name);
+				return;
+			}
+		}
+	} else {
+		Element elt = (Element) types;
+		if (elt.getType() != type)
+			return;
+		data.remove(name);
+	}
+}
+
+/** Empties the Cache. */
+public synchronized void
+clearCache() {
+	data.clear();
+}
+
+/**
+ * Adds a record to the Cache.
+ * @param r The record to be added
+ * @param cred The credibility of the record
+ * @param o The source of the record (this could be a Message, for example)
+ * @see Record
+ */
+public synchronized void
+addRecord(Record r, int cred, Object o) {
+	Name name = r.getName();
+	int type = r.getRRsetType();
+	if (!Type.isRR(type))
+		return;
+	Element element = findElement(name, type, cred);
+	if (element == null) {
+		CacheRRset crrset = new CacheRRset(r, cred, maxcache);
+		addRRset(crrset, cred);
+	} else if (element.compareCredibility(cred) == 0) {
+		if (element instanceof CacheRRset) {
+			CacheRRset crrset = (CacheRRset) element;
+			crrset.addRR(r);
+		}
+	}
+}
+
+/**
+ * Adds an RRset to the Cache.
+ * @param rrset The RRset to be added
+ * @param cred The credibility of these records
+ * @see RRset
+ */
+public synchronized void
+addRRset(RRset rrset, int cred) {
+	long ttl = rrset.getTTL();
+	Name name = rrset.getName();
+	int type = rrset.getType();
+	Element element = findElement(name, type, 0);
+	if (ttl == 0) {
+		if (element != null && element.compareCredibility(cred) <= 0)
+			removeElement(name, type);
+	} else {
+		if (element != null && element.compareCredibility(cred) <= 0)
+			element = null;
+		if (element == null) {
+			CacheRRset crrset;
+			if (rrset instanceof CacheRRset)
+				crrset = (CacheRRset) rrset;
+			else
+				crrset = new CacheRRset(rrset, cred, maxcache);
+			addElement(name, crrset);
+		}
+	}
+}
+
+/**
+ * Adds a negative entry to the Cache.
+ * @param name The name of the negative entry
+ * @param type The type of the negative entry
+ * @param soa The SOA record to add to the negative cache entry, or null.
+ * The negative cache ttl is derived from the SOA.
+ * @param cred The credibility of the negative entry
+ */
+public synchronized void
+addNegative(Name name, int type, SOARecord soa, int cred) {
+	long ttl = 0;
+	if (soa != null)
+		ttl = soa.getTTL();
+	Element element = findElement(name, type, 0);
+	if (ttl == 0) {
+		if (element != null && element.compareCredibility(cred) <= 0)
+			removeElement(name, type);
+	} else {
+		if (element != null && element.compareCredibility(cred) <= 0)
+			element = null;
+		if (element == null)
+			addElement(name, new NegativeElement(name, type,
+							     soa, cred,
+							     maxncache));
+	}
+}
+
+/**
+ * Finds all matching sets or something that causes the lookup to stop.
+ */
+protected synchronized SetResponse
+lookup(Name name, int type, int minCred) {
+	int labels;
+	int tlabels;
+	Element element;
+	Name tname;
+	Object types;
+	SetResponse sr;
+
+	labels = name.labels();
+
+	for (tlabels = labels; tlabels >= 1; tlabels--) {
+		boolean isRoot = (tlabels == 1);
+		boolean isExact = (tlabels == labels);
+
+		if (isRoot)
+			tname = Name.root;
+		else if (isExact)
+			tname = name;
+		else
+			tname = new Name(name, labels - tlabels);
+
+		types = data.get(tname);
+		if (types == null)
+			continue;
+
+		/*
+		 * If this is the name, look for the actual type or a CNAME
+		 * (unless it's an ANY query, where we return everything).
+		 * Otherwise, look for a DNAME.
+		 */
+		if (isExact && type == Type.ANY) {
+			sr = new SetResponse(SetResponse.SUCCESSFUL);
+			Element [] elements = allElements(types);
+			int added = 0;
+			for (int i = 0; i < elements.length; i++) {
+				element = elements[i];
+				if (element.expired()) {
+					removeElement(tname, element.getType());
+					continue;
+				}
+				if (!(element instanceof CacheRRset))
+					continue;
+				if (element.compareCredibility(minCred) < 0)
+					continue;
+				sr.addRRset((CacheRRset)element);
+				added++;
+			}
+			/* There were positive entries */
+			if (added > 0)
+				return sr;
+		} else if (isExact) {
+			element = oneElement(tname, types, type, minCred);
+			if (element != null &&
+			    element instanceof CacheRRset)
+			{
+				sr = new SetResponse(SetResponse.SUCCESSFUL);
+				sr.addRRset((CacheRRset) element);
+				return sr;
+			} else if (element != null) {
+				sr = new SetResponse(SetResponse.NXRRSET);
+				return sr;
+			}
+
+			element = oneElement(tname, types, Type.CNAME, minCred);
+			if (element != null &&
+			    element instanceof CacheRRset)
+			{
+				return new SetResponse(SetResponse.CNAME,
+						       (CacheRRset) element);
+			}
+		} else {
+			element = oneElement(tname, types, Type.DNAME, minCred);
+			if (element != null &&
+			    element instanceof CacheRRset)
+			{
+				return new SetResponse(SetResponse.DNAME,
+						       (CacheRRset) element);
+			}
+		}
+
+		/* Look for an NS */
+		element = oneElement(tname, types, Type.NS, minCred);
+		if (element != null && element instanceof CacheRRset)
+			return new SetResponse(SetResponse.DELEGATION,
+					       (CacheRRset) element);
+
+		/* Check for the special NXDOMAIN element. */
+		if (isExact) {
+			element = oneElement(tname, types, 0, minCred);
+			if (element != null)
+				return SetResponse.ofType(SetResponse.NXDOMAIN);
+		}
+
+	}
+	return SetResponse.ofType(SetResponse.UNKNOWN);
+}
+
+/**
+ * Looks up Records in the Cache.  This follows CNAMEs and handles negatively
+ * cached data.
+ * @param name The name to look up
+ * @param type The type to look up
+ * @param minCred The minimum acceptable credibility
+ * @return A SetResponse object
+ * @see SetResponse
+ * @see Credibility
+ */
+public SetResponse
+lookupRecords(Name name, int type, int minCred) {
+	return lookup(name, type, minCred);
+}
+
+private RRset []
+findRecords(Name name, int type, int minCred) {
+	SetResponse cr = lookupRecords(name, type, minCred);
+	if (cr.isSuccessful())
+		return cr.answers();
+	else
+		return null;
+}
+
+/**
+ * Looks up credible Records in the Cache (a wrapper around lookupRecords).
+ * Unlike lookupRecords, this given no indication of why failure occurred.
+ * @param name The name to look up
+ * @param type The type to look up
+ * @return An array of RRsets, or null
+ * @see Credibility
+ */
+public RRset []
+findRecords(Name name, int type) {
+	return findRecords(name, type, Credibility.NORMAL);
+}
+
+/**
+ * Looks up Records in the Cache (a wrapper around lookupRecords).  Unlike
+ * lookupRecords, this given no indication of why failure occurred.
+ * @param name The name to look up
+ * @param type The type to look up
+ * @return An array of RRsets, or null
+ * @see Credibility
+ */
+public RRset []
+findAnyRecords(Name name, int type) {
+	return findRecords(name, type, Credibility.GLUE);
+}
+
+private final int
+getCred(int section, boolean isAuth) {
+	if (section == Section.ANSWER) {
+		if (isAuth)
+			return Credibility.AUTH_ANSWER;
+		else
+			return Credibility.NONAUTH_ANSWER;
+	} else if (section == Section.AUTHORITY) {
+		if (isAuth)
+			return Credibility.AUTH_AUTHORITY;
+		else
+			return Credibility.NONAUTH_AUTHORITY;
+	} else if (section == Section.ADDITIONAL) {
+		return Credibility.ADDITIONAL;
+	} else
+		throw new IllegalArgumentException("getCred: invalid section");
+}
+
+private static void
+markAdditional(RRset rrset, Set names) {
+	Record first = rrset.first();
+	if (first.getAdditionalName() == null)
+		return;
+
+	Iterator it = rrset.rrs();
+	while (it.hasNext()) {
+		Record r = (Record) it.next();
+		Name name = r.getAdditionalName();
+		if (name != null)
+			names.add(name);
+	}
+}
+
+/**
+ * Adds all data from a Message into the Cache.  Each record is added with
+ * the appropriate credibility, and negative answers are cached as such.
+ * @param in The Message to be added
+ * @return A SetResponse that reflects what would be returned from a cache
+ * lookup, or null if nothing useful could be cached from the message.
+ * @see Message
+ */
+public SetResponse
+addMessage(Message in) {
+	boolean isAuth = in.getHeader().getFlag(Flags.AA);
+	Record question = in.getQuestion();
+	Name qname;
+	Name curname;
+	int qtype;
+	int qclass;
+	int cred;
+	int rcode = in.getHeader().getRcode();
+	boolean completed = false;
+	RRset [] answers, auth, addl;
+	SetResponse response = null;
+	boolean verbose = Options.check("verbosecache");
+	HashSet additionalNames;
+
+	if ((rcode != Rcode.NOERROR && rcode != Rcode.NXDOMAIN) ||
+	    question == null)
+		return null;
+
+	qname = question.getName();
+	qtype = question.getType();
+	qclass = question.getDClass();
+
+	curname = qname;
+
+	additionalNames = new HashSet();
+
+	answers = in.getSectionRRsets(Section.ANSWER);
+	for (int i = 0; i < answers.length; i++) {
+		if (answers[i].getDClass() != qclass)
+			continue;
+		int type = answers[i].getType();
+		Name name = answers[i].getName();
+		cred = getCred(Section.ANSWER, isAuth);
+		if ((type == qtype || qtype == Type.ANY) &&
+		    name.equals(curname))
+		{
+			addRRset(answers[i], cred);
+			completed = true;
+			if (curname == qname) {
+				if (response == null)
+					response = new SetResponse(
+							SetResponse.SUCCESSFUL);
+				response.addRRset(answers[i]);
+			}
+			markAdditional(answers[i], additionalNames);
+		} else if (type == Type.CNAME && name.equals(curname)) {
+			CNAMERecord cname;
+			addRRset(answers[i], cred);
+			if (curname == qname)
+				response = new SetResponse(SetResponse.CNAME,
+							   answers[i]);
+			cname = (CNAMERecord) answers[i].first();
+			curname = cname.getTarget();
+		} else if (type == Type.DNAME && curname.subdomain(name)) {
+			DNAMERecord dname;
+			addRRset(answers[i], cred);
+			if (curname == qname)
+				response = new SetResponse(SetResponse.DNAME,
+							   answers[i]);
+			dname = (DNAMERecord) answers[i].first();
+			try {
+				curname = curname.fromDNAME(dname);
+			}
+			catch (NameTooLongException e) {
+				break;
+			}
+		}
+	}
+
+	auth = in.getSectionRRsets(Section.AUTHORITY);
+	RRset soa = null, ns = null;
+	for (int i = 0; i < auth.length; i++) {
+		if (auth[i].getType() == Type.SOA &&
+		    curname.subdomain(auth[i].getName()))
+			soa = auth[i];
+		else if (auth[i].getType() == Type.NS &&
+			 curname.subdomain(auth[i].getName()))
+			ns = auth[i];
+	}
+	if (!completed) {
+		/* This is a negative response or a referral. */
+		int cachetype = (rcode == Rcode.NXDOMAIN) ? 0 : qtype;
+		if (rcode == Rcode.NXDOMAIN || soa != null || ns == null) {
+			/* Negative response */
+			cred = getCred(Section.AUTHORITY, isAuth);
+			SOARecord soarec = null;
+			if (soa != null)
+				soarec = (SOARecord) soa.first();
+			addNegative(curname, cachetype, soarec, cred);
+			if (response == null) {
+				int responseType;
+				if (rcode == Rcode.NXDOMAIN)
+					responseType = SetResponse.NXDOMAIN;
+				else
+					responseType = SetResponse.NXRRSET;
+				response = SetResponse.ofType(responseType);
+			}
+			/* DNSSEC records are not cached. */
+		} else {
+			/* Referral response */
+			cred = getCred(Section.AUTHORITY, isAuth);
+			addRRset(ns, cred);
+			markAdditional(ns, additionalNames);
+			if (response == null)
+				response = new SetResponse(
+							SetResponse.DELEGATION,
+							ns);
+		}
+	} else if (rcode == Rcode.NOERROR && ns != null) {
+		/* Cache the NS set from a positive response. */
+		cred = getCred(Section.AUTHORITY, isAuth);
+		addRRset(ns, cred);
+		markAdditional(ns, additionalNames);
+	}
+
+	addl = in.getSectionRRsets(Section.ADDITIONAL);
+	for (int i = 0; i < addl.length; i++) {
+		int type = addl[i].getType();
+		if (type != Type.A && type != Type.AAAA && type != Type.A6)
+			continue;
+		Name name = addl[i].getName();
+		if (!additionalNames.contains(name))
+			continue;
+		cred = getCred(Section.ADDITIONAL, isAuth);
+		addRRset(addl[i], cred);
+	}
+	if (verbose)
+		System.out.println("addMessage: " + response);
+	return (response);
+}
+
+/**
+ * Flushes an RRset from the cache
+ * @param name The name of the records to be flushed
+ * @param type The type of the records to be flushed
+ * @see RRset
+ */
+public void
+flushSet(Name name, int type) {
+	removeElement(name, type);
+}
+
+/**
+ * Flushes all RRsets with a given name from the cache
+ * @param name The name of the records to be flushed
+ * @see RRset
+ */
+public void
+flushName(Name name) {
+	removeName(name);
+}
+
+/**
+ * Sets the maximum length of time that a negative response will be stored
+ * in this Cache.  A negative value disables this feature (that is, sets
+ * no limit).
+ */
+public void
+setMaxNCache(int seconds) {
+	maxncache = seconds;
+}
+
+/**
+ * Gets the maximum length of time that a negative response will be stored
+ * in this Cache.  A negative value indicates no limit.
+ */
+public int
+getMaxNCache() {
+	return maxncache;
+}
+
+/**
+ * Sets the maximum length of time that records will be stored in this
+ * Cache.  A negative value disables this feature (that is, sets no limit).
+ */
+public void
+setMaxCache(int seconds) {
+	maxcache = seconds;
+}
+
+/**
+ * Gets the maximum length of time that records will be stored
+ * in this Cache.  A negative value indicates no limit.
+ */
+public int
+getMaxCache() {
+	return maxcache;
+}
+
+/**
+ * Gets the current number of entries in the Cache, where an entry consists
+ * of all records with a specific Name.
+ */
+public int
+getSize() {
+	return data.size();
+}
+
+/**
+ * Gets the maximum number of entries in the Cache, where an entry consists
+ * of all records with a specific Name.  A negative value is treated as an
+ * infinite limit.
+ */
+public int
+getMaxEntries() {
+	return data.getMaxSize();
+}
+
+/**
+ * Sets the maximum number of entries in the Cache, where an entry consists
+ * of all records with a specific Name.  A negative value is treated as an
+ * infinite limit.
+ *
+ * Note that setting this to a value lower than the current number
+ * of entries will not cause the Cache to shrink immediately.
+ *
+ * The default maximum number of entries is 50000.
+ *
+ * @param entries The maximum number of entries in the Cache.
+ */
+public void
+setMaxEntries(int entries) {
+	data.setMaxSize(entries);
+}
+
+/**
+ * Returns the DNS class of this cache.
+ */
+public int
+getDClass() {
+	return dclass;
+}
+
+/**
+ * Returns the contents of the Cache as a string.
+ */ 
+public String
+toString() {
+	StringBuffer sb = new StringBuffer();
+	synchronized (this) {
+		Iterator it = data.values().iterator();
+		while (it.hasNext()) {
+			Element [] elements = allElements(it.next());
+			for (int i = 0; i < elements.length; i++) {
+				sb.append(elements[i]);
+				sb.append("\n");
+			}
+		}
+	}
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/Client.java b/src/org/xbill/DNS/Client.java
new file mode 100644
index 0000000..2eef44f
--- /dev/null
+++ b/src/org/xbill/DNS/Client.java
@@ -0,0 +1,58 @@
+// Copyright (c) 2005 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import java.nio.channels.*;
+import org.xbill.DNS.utils.hexdump;
+
+class Client {
+
+protected long endTime;
+protected SelectionKey key;
+
+protected
+Client(SelectableChannel channel, long endTime) throws IOException {
+	boolean done = false;
+	Selector selector = null;
+	this.endTime = endTime;
+	try {
+		selector = Selector.open();
+		channel.configureBlocking(false);
+		key = channel.register(selector, SelectionKey.OP_READ);
+		done = true;
+	}
+	finally {
+		if (!done && selector != null)
+			selector.close();
+		if (!done)
+			channel.close();
+	}
+}
+
+static protected void
+blockUntil(SelectionKey key, long endTime) throws IOException {
+	long timeout = endTime - System.currentTimeMillis();
+	int nkeys = 0;
+	if (timeout > 0)
+		nkeys = key.selector().select(timeout);
+	else if (timeout == 0)
+		nkeys = key.selector().selectNow();
+	if (nkeys == 0)
+		throw new SocketTimeoutException();
+}
+
+static protected void
+verboseLog(String prefix, byte [] data) {
+	if (Options.check("verbosemsg"))
+		System.err.println(hexdump.dump(prefix, data));
+}
+
+void
+cleanup() throws IOException {
+	key.selector().close();
+	key.channel().close();
+}
+
+}
diff --git a/src/org/xbill/DNS/ClientSubnetOption.java b/src/org/xbill/DNS/ClientSubnetOption.java
new file mode 100644
index 0000000..4a98a12
--- /dev/null
+++ b/src/org/xbill/DNS/ClientSubnetOption.java
@@ -0,0 +1,175 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.net.*;
+import java.util.regex.*;
+
+/**
+ * The Client Subnet EDNS Option, defined in
+ * http://tools.ietf.org/html/draft-vandergaast-edns-client-subnet-00
+ * ("Client subnet in DNS requests").
+ *
+ * The option is used to convey information about the IP address of the
+ * originating client, so that an authoritative server can make decisions
+ * based on this address, rather than the address of the intermediate
+ * caching name server.
+ *
+ * The option is transmitted as part of an OPTRecord in the additional section
+ * of a DNS message, as defined by RFC 2671 (EDNS0).
+ * 
+ * An option code has not been assigned by IANA; the value 20730 (used here) is
+ * also used by several other implementations.
+ *
+ * The wire format of the option contains a 2-byte length field (1 for IPv4, 2
+ * for IPv6), a 1-byte source netmask, a 1-byte scope netmask, and an address
+ * truncated to the source netmask length (where the final octet is padded with
+ * bits set to 0)
+ * 
+ *
+ * @see OPTRecord
+ * 
+ * @author Brian Wellington
+ * @author Ming Zhou &lt;mizhou@bnivideo.com&gt;, Beaumaris Networks
+ */
+public class ClientSubnetOption extends EDNSOption {
+
+private static final long serialVersionUID = -3868158449890266347L;
+
+private int family;
+private int sourceNetmask;
+private int scopeNetmask;
+private InetAddress address;
+
+ClientSubnetOption() {
+	super(EDNSOption.Code.CLIENT_SUBNET);
+}
+
+private static int
+checkMaskLength(String field, int family, int val) {
+	int max = Address.addressLength(family) * 8;
+	if (val < 0 || val > max)
+		throw new IllegalArgumentException("\"" + field + "\" " + val +
+						   " must be in the range " +
+						   "[0.." + max + "]");
+	return val;
+}
+
+/**
+ * Construct a Client Subnet option.  Note that the number of significant bits in
+ * the address must not be greater than the supplied source netmask.
+ * XXX something about Java's mapped addresses
+ * @param sourceNetmask The length of the netmask pertaining to the query.
+ * In replies, it mirrors the same value as in the requests.
+ * @param scopeNetmask The length of the netmask pertaining to the reply.
+ * In requests, it MUST be set to 0.  In responses, this may or may not match
+ * the source netmask.
+ * @param address The address of the client.
+ */
+public 
+ClientSubnetOption(int sourceNetmask, int scopeNetmask, InetAddress address) {
+	super(EDNSOption.Code.CLIENT_SUBNET);
+
+	this.family = Address.familyOf(address);
+	this.sourceNetmask = checkMaskLength("source netmask", this.family,
+					     sourceNetmask);
+	this.scopeNetmask = checkMaskLength("scope netmask", this.family,
+					     scopeNetmask);
+	this.address = Address.truncate(address, sourceNetmask);
+
+	if (!address.equals(this.address))
+		throw new IllegalArgumentException("source netmask is not " +
+						   "valid for address");
+}
+
+/**
+ * Construct a Client Subnet option with scope netmask set to 0.
+ * @param sourceNetmask The length of the netmask pertaining to the query.
+ * In replies, it mirrors the same value as in the requests.
+ * @param address The address of the client.
+ * @see ClientSubnetOption
+ */
+public 
+ClientSubnetOption(int sourceNetmask, InetAddress address) {
+	this(sourceNetmask, 0, address);
+}
+
+/**
+ * Returns the family of the network address.  This will be either IPv4 (1)
+ * or IPv6 (2).
+ */
+public int 
+getFamily() {
+	return family;
+}
+
+/** Returns the source netmask. */
+public int 
+getSourceNetmask() {
+	return sourceNetmask;
+}
+
+/** Returns the scope netmask. */
+public int 
+getScopeNetmask() {
+	return scopeNetmask;
+}
+
+/** Returns the IP address of the client. */
+public InetAddress 
+getAddress() {
+	return address;
+}
+
+void 
+optionFromWire(DNSInput in) throws WireParseException {
+	family = in.readU16();
+	if (family != Address.IPv4 && family != Address.IPv6)
+		throw new WireParseException("unknown address family");
+	sourceNetmask = in.readU8();
+	if (sourceNetmask > Address.addressLength(family) * 8)
+		throw new WireParseException("invalid source netmask");
+	scopeNetmask = in.readU8();
+	if (scopeNetmask > Address.addressLength(family) * 8)
+		throw new WireParseException("invalid scope netmask");
+
+	// Read the truncated address
+	byte [] addr = in.readByteArray();
+	if (addr.length != (sourceNetmask + 7) / 8)
+		throw new WireParseException("invalid address");
+
+	// Convert it to a full length address.
+	byte [] fulladdr = new byte[Address.addressLength(family)];
+	System.arraycopy(addr, 0, fulladdr, 0, addr.length);
+
+	try {
+		address = InetAddress.getByAddress(fulladdr);
+	} catch (UnknownHostException e) {
+		throw new WireParseException("invalid address", e);
+	}
+
+	InetAddress tmp = Address.truncate(address, sourceNetmask);
+	if (!tmp.equals(address))
+		throw new WireParseException("invalid padding");
+}
+
+void 
+optionToWire(DNSOutput out) {
+	out.writeU16(family);
+	out.writeU8(sourceNetmask);
+	out.writeU8(scopeNetmask);
+	out.writeByteArray(address.getAddress(), 0, (sourceNetmask + 7) / 8);
+}
+
+String 
+optionToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(address.getHostAddress());
+	sb.append("/");
+	sb.append(sourceNetmask);
+	sb.append(", scope netmask ");
+	sb.append(scopeNetmask);
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/Compression.java b/src/org/xbill/DNS/Compression.java
new file mode 100644
index 0000000..e3e81c0
--- /dev/null
+++ b/src/org/xbill/DNS/Compression.java
@@ -0,0 +1,72 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * DNS Name Compression object.
+ * @see Message
+ * @see Name
+ *
+ * @author Brian Wellington
+ */
+
+public class Compression {
+
+private static class Entry {
+	Name name;
+	int pos;
+	Entry next;
+}
+
+private static final int TABLE_SIZE = 17;
+private static final int MAX_POINTER = 0x3FFF;
+private Entry [] table;
+private boolean verbose = Options.check("verbosecompression");
+
+/**
+ * Creates a new Compression object.
+ */
+public
+Compression() {
+	table = new Entry[TABLE_SIZE];
+}
+
+/**
+ * Adds a compression entry mapping a name to a position in a message.
+ * @param pos The position at which the name is added.
+ * @param name The name being added to the message.
+ */
+public void
+add(int pos, Name name) {
+	if (pos > MAX_POINTER)
+		return;
+	int row = (name.hashCode() & 0x7FFFFFFF) % TABLE_SIZE;
+	Entry entry = new Entry();
+	entry.name = name;
+	entry.pos = pos;
+	entry.next = table[row];
+	table[row] = entry;
+	if (verbose)
+		System.err.println("Adding " + name + " at " + pos);
+}
+
+/**
+ * Retrieves the position of the given name, if it has been previously
+ * included in the message.
+ * @param name The name to find in the compression table.
+ * @return The position of the name, or -1 if not found.
+ */
+public int
+get(Name name) {
+	int row = (name.hashCode() & 0x7FFFFFFF) % TABLE_SIZE;
+	int pos = -1;
+	for (Entry entry = table[row]; entry != null; entry = entry.next) {
+		if (entry.name.equals(name))
+			pos = entry.pos;
+	}
+	if (verbose)
+		System.err.println("Looking for " + name + ", found " + pos);
+	return pos;
+}
+
+}
diff --git a/src/org/xbill/DNS/Credibility.java b/src/org/xbill/DNS/Credibility.java
new file mode 100644
index 0000000..fa10686
--- /dev/null
+++ b/src/org/xbill/DNS/Credibility.java
@@ -0,0 +1,50 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants relating to the credibility of cached data, which is based on
+ * the data's source.  The constants NORMAL and ANY should be used by most
+ * callers.
+ * @see Cache
+ * @see Section
+ *
+ * @author Brian Wellington
+ */
+
+public final class Credibility {
+
+private
+Credibility() {}
+
+/** A hint or cache file on disk. */
+public static final int HINT			= 0;
+
+/** The additional section of a response. */
+public static final int ADDITIONAL		= 1;
+
+/** The additional section of a response. */
+public static final int GLUE			= 2;
+
+/** The authority section of a nonauthoritative response. */
+public static final int NONAUTH_AUTHORITY	= 3;
+
+/** The answer section of a nonauthoritative response. */
+public static final int NONAUTH_ANSWER		= 3;
+
+/** The authority section of an authoritative response. */
+public static final int AUTH_AUTHORITY		= 4;
+
+/** The answer section of a authoritative response. */
+public static final int AUTH_ANSWER		= 4;
+
+/** A zone. */
+public static final int ZONE			= 5;
+
+/** Credible data. */
+public static final int NORMAL			= 3;
+
+/** Data not required to be credible. */
+public static final int ANY			= 1;
+
+}
diff --git a/src/org/xbill/DNS/DClass.java b/src/org/xbill/DNS/DClass.java
new file mode 100644
index 0000000..22180cf
--- /dev/null
+++ b/src/org/xbill/DNS/DClass.java
@@ -0,0 +1,92 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to DNS classes.  This is called DClass
+ * to avoid confusion with Class.
+ *
+ * @author Brian Wellington
+ */
+
+public final class DClass {
+
+/** Internet */
+public static final int IN		= 1;
+
+/** Chaos network (MIT) */
+public static final int CH		= 3;
+
+/** Chaos network (MIT, alternate name) */
+public static final int CHAOS		= 3;
+
+/** Hesiod name server (MIT) */
+public static final int HS		= 4;
+
+/** Hesiod name server (MIT, alternate name) */
+public static final int HESIOD		= 4;
+
+/** Special value used in dynamic update messages */
+public static final int NONE		= 254;
+
+/** Matches any class */
+public static final int ANY		= 255;
+
+private static class DClassMnemonic extends Mnemonic {
+	public
+	DClassMnemonic() {
+		super("DClass", CASE_UPPER);
+		setPrefix("CLASS");
+	}
+
+	public void
+	check(int val) {
+		DClass.check(val);
+	}
+}
+
+private static Mnemonic classes = new DClassMnemonic();
+
+static {
+	classes.add(IN, "IN");
+	classes.add(CH, "CH");
+	classes.addAlias(CH, "CHAOS");
+	classes.add(HS, "HS");
+	classes.addAlias(HS, "HESIOD");
+	classes.add(NONE, "NONE");
+	classes.add(ANY, "ANY");
+}
+
+private
+DClass() {}
+
+/**
+ * Checks that a numeric DClass is valid.
+ * @throws InvalidDClassException The class is out of range.
+ */
+public static void
+check(int i) {
+	if (i < 0 || i > 0xFFFF)
+		throw new InvalidDClassException(i);
+}
+
+/**
+ * Converts a numeric DClass into a String
+ * @return The canonical string representation of the class
+ * @throws InvalidDClassException The class is out of range.
+ */
+public static String
+string(int i) {
+	return classes.getText(i);
+}
+
+/**
+ * Converts a String representation of a DClass into its numeric value
+ * @return The class code, or -1 on error.
+ */
+public static int
+value(String s) {
+	return classes.getValue(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/DHCIDRecord.java b/src/org/xbill/DNS/DHCIDRecord.java
new file mode 100644
index 0000000..e160a8c
--- /dev/null
+++ b/src/org/xbill/DNS/DHCIDRecord.java
@@ -0,0 +1,65 @@
+// Copyright (c) 2008 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.base64;
+
+/**
+ * DHCID - Dynamic Host Configuration Protocol (DHCP) ID (RFC 4701)
+ *
+ * @author Brian Wellington
+ */
+
+public class DHCIDRecord extends Record {
+
+private static final long serialVersionUID = -8214820200808997707L;
+
+private byte [] data;
+
+DHCIDRecord() {}
+
+Record
+getObject() {
+	return new DHCIDRecord();
+}
+
+/**
+ * Creates an DHCID Record from the given data
+ * @param data The binary data, which is opaque to DNS.
+ */
+public
+DHCIDRecord(Name name, int dclass, long ttl, byte [] data) {
+	super(name, Type.DHCID, dclass, ttl);
+	this.data = data;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	data = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	data = st.getBase64();
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(data);
+}
+
+String
+rrToString() {
+	return base64.toString(data);
+}
+
+/**
+ * Returns the binary data.
+ */
+public byte []
+getData() {
+	return data;
+}
+
+}
diff --git a/src/org/xbill/DNS/DLVRecord.java b/src/org/xbill/DNS/DLVRecord.java
new file mode 100644
index 0000000..8acc90f
--- /dev/null
+++ b/src/org/xbill/DNS/DLVRecord.java
@@ -0,0 +1,132 @@
+// Copyright (c) 2002-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * DLV - contains a Delegation Lookaside Validation record, which acts
+ * as the equivalent of a DS record in a lookaside zone.
+ * @see DNSSEC
+ * @see DSRecord
+ *
+ * @author David Blacka
+ * @author Brian Wellington
+ */
+
+public class DLVRecord extends Record {
+
+public static final int SHA1_DIGEST_ID = DSRecord.Digest.SHA1;
+public static final int SHA256_DIGEST_ID = DSRecord.Digest.SHA1;
+
+private static final long serialVersionUID = 1960742375677534148L;
+
+private int footprint;
+private int alg;
+private int digestid;
+private byte [] digest;
+
+DLVRecord() {}
+
+Record
+getObject() {
+	return new DLVRecord();
+}
+
+/**
+ * Creates a DLV Record from the given data
+ * @param footprint The original KEY record's footprint (keyid).
+ * @param alg The original key algorithm.
+ * @param digestid The digest id code.
+ * @param digest A hash of the original key.
+ */
+public
+DLVRecord(Name name, int dclass, long ttl, int footprint, int alg,
+	  int digestid, byte [] digest)
+{
+	super(name, Type.DLV, dclass, ttl);
+	this.footprint = checkU16("footprint", footprint);
+	this.alg = checkU8("alg", alg);
+	this.digestid = checkU8("digestid", digestid);
+	this.digest = digest;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	footprint = in.readU16();
+	alg = in.readU8();
+	digestid = in.readU8();
+	digest = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	footprint = st.getUInt16();
+	alg = st.getUInt8();
+	digestid = st.getUInt8();
+	digest = st.getHex();
+}
+
+/**
+ * Converts rdata to a String
+ */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(footprint);
+	sb.append(" ");
+	sb.append(alg);
+	sb.append(" ");
+	sb.append(digestid);
+	if (digest != null) {
+		sb.append(" ");
+		sb.append(base16.toString(digest));
+	}
+
+	return sb.toString();
+}
+
+/**
+ * Returns the key's algorithm.
+ */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ *  Returns the key's Digest ID.
+ */
+public int
+getDigestID()
+{
+	return digestid;
+}
+  
+/**
+ * Returns the binary hash of the key.
+ */
+public byte []
+getDigest() {
+	return digest;
+}
+
+/**
+ * Returns the key's footprint.
+ */
+public int
+getFootprint() {
+	return footprint;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(footprint);
+	out.writeU8(alg);
+	out.writeU8(digestid);
+	if (digest != null)
+		out.writeByteArray(digest);
+}
+
+}
diff --git a/src/org/xbill/DNS/DNAMERecord.java b/src/org/xbill/DNS/DNAMERecord.java
new file mode 100644
index 0000000..cbb322f
--- /dev/null
+++ b/src/org/xbill/DNS/DNAMERecord.java
@@ -0,0 +1,45 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * DNAME Record  - maps a nonterminal alias (subtree) to a different domain
+ *
+ * @author Brian Wellington
+ */
+
+public class DNAMERecord extends SingleNameBase {
+
+private static final long serialVersionUID = 2670767677200844154L;
+
+DNAMERecord() {}
+
+Record
+getObject() {
+	return new DNAMERecord();
+}
+
+/**
+ * Creates a new DNAMERecord with the given data
+ * @param alias The name to which the DNAME alias points
+ */
+public
+DNAMERecord(Name name, int dclass, long ttl, Name alias) {
+	super(name, Type.DNAME, dclass, ttl, alias, "alias");
+}
+
+/**
+ * Gets the target of the DNAME Record
+ */
+public Name
+getTarget() {
+	return getSingleName();
+}
+
+/** Gets the alias specified by the DNAME Record */
+public Name
+getAlias() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/DNSInput.java b/src/org/xbill/DNS/DNSInput.java
new file mode 100644
index 0000000..d3134ed
--- /dev/null
+++ b/src/org/xbill/DNS/DNSInput.java
@@ -0,0 +1,239 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An class for parsing DNS messages.
+ *
+ * @author Brian Wellington
+ */
+
+public class DNSInput {
+
+private byte [] array;
+private int pos;
+private int end;
+private int saved_pos;
+private int saved_end;
+
+/**
+ * Creates a new DNSInput
+ * @param input The byte array to read from
+ */
+public
+DNSInput(byte [] input) {
+	array = input;
+	pos = 0;
+	end = array.length;
+	saved_pos = -1;
+	saved_end = -1;
+}
+
+/**
+ * Returns the current position.
+ */
+public int
+current() {
+	return pos;
+}
+
+/**
+ * Returns the number of bytes that can be read from this stream before
+ * reaching the end.
+ */
+public int
+remaining() {
+	return end - pos;
+}
+
+private void
+require(int n) throws WireParseException{
+	if (n > remaining()) {
+		throw new WireParseException("end of input");
+	}
+}
+
+/**
+ * Marks the following bytes in the stream as active.
+ * @param len The number of bytes in the active region.
+ * @throws IllegalArgumentException The number of bytes in the active region
+ * is longer than the remainder of the input.
+ */
+public void
+setActive(int len) {
+	if (len > array.length - pos) {
+		throw new IllegalArgumentException("cannot set active " +
+						   "region past end of input");
+	}
+	end = pos + len;
+}
+
+/**
+ * Clears the active region of the string.  Further operations are not
+ * restricted to part of the input.
+ */
+public void
+clearActive() {
+	end = array.length;
+}
+
+/**
+ * Returns the position of the end of the current active region.
+ */
+public int
+saveActive() {
+	return end;
+}
+
+/**
+ * Restores the previously set active region.  This differs from setActive() in
+ * that restoreActive() takes an absolute position, and setActive takes an
+ * offset from the current location.
+ * @param pos The end of the active region.
+ */
+public void
+restoreActive(int pos) {
+	if (pos > array.length) {
+		throw new IllegalArgumentException("cannot set active " +
+						   "region past end of input");
+	}
+	end = pos;
+}
+
+/**
+ * Resets the current position of the input stream to the specified index,
+ * and clears the active region.
+ * @param index The position to continue parsing at.
+ * @throws IllegalArgumentException The index is not within the input.
+ */
+public void
+jump(int index) {
+	if (index >= array.length) {
+		throw new IllegalArgumentException("cannot jump past " +
+						   "end of input");
+	}
+	pos = index;
+	end = array.length;
+}
+
+/**
+ * Saves the current state of the input stream.  Both the current position and
+ * the end of the active region are saved.
+ * @throws IllegalArgumentException The index is not within the input.
+ */
+public void
+save() {
+	saved_pos = pos;
+	saved_end = end;
+}
+
+/**
+ * Restores the input stream to its state before the call to {@link #save}.
+ */
+public void
+restore() {
+	if (saved_pos < 0) {
+		throw new IllegalStateException("no previous state");
+	}
+	pos = saved_pos;
+	end = saved_end;
+	saved_pos = -1;
+	saved_end = -1;
+}
+
+/**
+ * Reads an unsigned 8 bit value from the stream, as an int.
+ * @return An unsigned 8 bit value.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public int
+readU8() throws WireParseException {
+	require(1);
+	return (array[pos++] & 0xFF);
+}
+
+/**
+ * Reads an unsigned 16 bit value from the stream, as an int.
+ * @return An unsigned 16 bit value.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public int
+readU16() throws WireParseException {
+	require(2);
+	int b1 = array[pos++] & 0xFF;
+	int b2 = array[pos++] & 0xFF;
+	return ((b1 << 8) + b2);
+}
+
+/**
+ * Reads an unsigned 32 bit value from the stream, as a long.
+ * @return An unsigned 32 bit value.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public long
+readU32() throws WireParseException {
+	require(4);
+	int b1 = array[pos++] & 0xFF;
+	int b2 = array[pos++] & 0xFF;
+	int b3 = array[pos++] & 0xFF;
+	int b4 = array[pos++] & 0xFF;
+	return (((long)b1 << 24) + (b2 << 16) + (b3 << 8) + b4);
+}
+
+/**
+ * Reads a byte array of a specified length from the stream into an existing
+ * array.
+ * @param b The array to read into.
+ * @param off The offset of the array to start copying data into.
+ * @param len The number of bytes to copy.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public void
+readByteArray(byte [] b, int off, int len) throws WireParseException {
+	require(len);
+	System.arraycopy(array, pos, b, off, len);
+	pos += len;
+}
+
+/**
+ * Reads a byte array of a specified length from the stream.
+ * @return The byte array.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public byte []
+readByteArray(int len) throws WireParseException {
+	require(len);
+	byte [] out = new byte[len];
+	System.arraycopy(array, pos, out, 0, len);
+	pos += len;
+	return out;
+}
+
+/**
+ * Reads a byte array consisting of the remainder of the stream (or the
+ * active region, if one is set.
+ * @return The byte array.
+ */
+public byte []
+readByteArray() {
+	int len = remaining();
+	byte [] out = new byte[len];
+	System.arraycopy(array, pos, out, 0, len);
+	pos += len;
+	return out;
+}
+
+/**
+ * Reads a counted string from the stream.  A counted string is a one byte
+ * value indicating string length, followed by bytes of data.
+ * @return A byte array containing the string.
+ * @throws WireParseException The end of the stream was reached.
+ */
+public byte []
+readCountedString() throws WireParseException {
+	require(1);
+	int len = array[pos++] & 0xFF;
+	return readByteArray(len);
+}
+
+}
diff --git a/src/org/xbill/DNS/DNSKEYRecord.java b/src/org/xbill/DNS/DNSKEYRecord.java
new file mode 100644
index 0000000..6e9bafd
--- /dev/null
+++ b/src/org/xbill/DNS/DNSKEYRecord.java
@@ -0,0 +1,91 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.security.PublicKey;
+
+/**
+ * Key - contains a cryptographic public key for use by DNS.
+ * The data can be converted to objects implementing
+ * java.security.interfaces.PublicKey
+ * @see DNSSEC
+ *
+ * @author Brian Wellington
+ */
+
+public class DNSKEYRecord extends KEYBase {
+
+public static class Protocol {
+	private Protocol() {}
+
+	/** Key will be used for DNSSEC */
+	public static final int DNSSEC = 3;
+}
+
+public static class Flags {
+	private Flags() {}
+
+	/** Key is a zone key */
+	public static final int ZONE_KEY = 0x100;
+
+	/** Key is a secure entry point key */
+	public static final int SEP_KEY = 0x1;
+
+	/** Key has been revoked */
+	public static final int REVOKE = 0x80;
+}
+
+private static final long serialVersionUID = -8679800040426675002L;
+
+DNSKEYRecord() {}
+
+Record
+getObject() {
+	return new DNSKEYRecord();
+}
+
+/**
+ * Creates a DNSKEY Record from the given data
+ * @param flags Flags describing the key's properties
+ * @param proto The protocol that the key was created for
+ * @param alg The key's algorithm
+ * @param key Binary representation of the key
+ */
+public
+DNSKEYRecord(Name name, int dclass, long ttl, int flags, int proto, int alg,
+	     byte [] key)
+{
+	super(name, Type.DNSKEY, dclass, ttl, flags, proto, alg, key);
+}
+
+/**
+ * Creates a DNSKEY Record from the given data
+ * @param flags Flags describing the key's properties
+ * @param proto The protocol that the key was created for
+ * @param alg The key's algorithm
+ * @param key The key as a PublicKey
+ * @throws DNSSEC.DNSSECException The PublicKey could not be converted into DNS
+ * format.
+ */
+public
+DNSKEYRecord(Name name, int dclass, long ttl, int flags, int proto, int alg,
+	     PublicKey key) throws DNSSEC.DNSSECException
+{
+	super(name, Type.DNSKEY, dclass, ttl, flags, proto, alg,
+	      DNSSEC.fromPublicKey(key, alg));
+	publicKey = key;
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	flags = st.getUInt16();
+	proto = st.getUInt8();
+	String algString = st.getString();
+	alg = DNSSEC.Algorithm.value(algString);
+	if (alg < 0)
+		throw st.exception("Invalid algorithm: " + algString);
+	key = st.getBase64();
+}
+
+}
diff --git a/src/org/xbill/DNS/DNSOutput.java b/src/org/xbill/DNS/DNSOutput.java
new file mode 100644
index 0000000..29a8f68
--- /dev/null
+++ b/src/org/xbill/DNS/DNSOutput.java
@@ -0,0 +1,203 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * A class for rendering DNS messages.
+ *
+ * @author Brian Wellington
+ */
+
+
+public class DNSOutput {
+
+private byte [] array;
+private int pos;
+private int saved_pos;
+
+/**
+ * Create a new DNSOutput with a specified size.
+ * @param size The initial size
+ */
+public
+DNSOutput(int size) {
+	array = new byte[size];
+	pos = 0;
+	saved_pos = -1;
+}
+
+/**
+ * Create a new DNSOutput
+ */
+public
+DNSOutput() {
+	this(32);
+}
+
+/**
+ * Returns the current position.
+ */
+public int
+current() {
+	return pos;
+}
+
+private void
+check(long val, int bits) {
+	long max = 1;
+	max <<= bits;
+	if (val < 0 || val > max) {
+		throw new IllegalArgumentException(val + " out of range for " +
+						   bits + " bit value");
+	}
+}
+
+private void
+need(int n) {
+	if (array.length - pos >= n) {
+		return;
+	}
+	int newsize = array.length * 2;
+	if (newsize < pos + n) {
+		newsize = pos + n;
+	}
+	byte [] newarray = new byte[newsize];
+	System.arraycopy(array, 0, newarray, 0, pos);
+	array = newarray;
+}
+
+/**
+ * Resets the current position of the output stream to the specified index.
+ * @param index The new current position.
+ * @throws IllegalArgumentException The index is not within the output.
+ */
+public void
+jump(int index) {
+	if (index > pos) {
+		throw new IllegalArgumentException("cannot jump past " +
+						   "end of data");
+	}
+	pos = index;
+}
+
+/**
+ * Saves the current state of the output stream.
+ * @throws IllegalArgumentException The index is not within the output.
+ */
+public void
+save() {
+	saved_pos = pos;
+}
+
+/**
+ * Restores the input stream to its state before the call to {@link #save}.
+ */
+public void
+restore() {
+	if (saved_pos < 0) {
+		throw new IllegalStateException("no previous state");
+	}
+	pos = saved_pos;
+	saved_pos = -1;
+}
+
+/**
+ * Writes an unsigned 8 bit value to the stream.
+ * @param val The value to be written
+ */
+public void
+writeU8(int val) {
+	check(val, 8);
+	need(1);
+	array[pos++] = (byte)(val & 0xFF);
+}
+
+/**
+ * Writes an unsigned 16 bit value to the stream.
+ * @param val The value to be written
+ */
+public void
+writeU16(int val) {
+	check(val, 16);
+	need(2);
+	array[pos++] = (byte)((val >>> 8) & 0xFF);
+	array[pos++] = (byte)(val & 0xFF);
+}
+
+/**
+ * Writes an unsigned 16 bit value to the specified position in the stream.
+ * @param val The value to be written
+ * @param where The position to write the value.
+ */
+public void
+writeU16At(int val, int where) {
+	check(val, 16);
+	if (where > pos - 2)
+		throw new IllegalArgumentException("cannot write past " +
+						   "end of data");
+	array[where++] = (byte)((val >>> 8) & 0xFF);
+	array[where++] = (byte)(val & 0xFF);
+}
+
+/**
+ * Writes an unsigned 32 bit value to the stream.
+ * @param val The value to be written
+ */
+public void
+writeU32(long val) {
+	check(val, 32);
+	need(4);
+	array[pos++] = (byte)((val >>> 24) & 0xFF);
+	array[pos++] = (byte)((val >>> 16) & 0xFF);
+	array[pos++] = (byte)((val >>> 8) & 0xFF);
+	array[pos++] = (byte)(val & 0xFF);
+}
+
+/**
+ * Writes a byte array to the stream.
+ * @param b The array to write.
+ * @param off The offset of the array to start copying data from.
+ * @param len The number of bytes to write.
+ */
+public void
+writeByteArray(byte [] b, int off, int len) {
+	need(len);
+	System.arraycopy(b, off, array, pos, len);
+	pos += len;
+}
+
+/**
+ * Writes a byte array to the stream.
+ * @param b The array to write.
+ */
+public void
+writeByteArray(byte [] b) {
+	writeByteArray(b, 0, b.length);
+}
+
+/**
+ * Writes a counted string from the stream.  A counted string is a one byte
+ * value indicating string length, followed by bytes of data.
+ * @param s The string to write.
+ */
+public void
+writeCountedString(byte [] s) {
+	if (s.length > 0xFF) {
+		throw new IllegalArgumentException("Invalid counted string");
+	}
+	need(1 + s.length);
+	array[pos++] = (byte)(s.length & 0xFF);
+	writeByteArray(s, 0, s.length);
+}
+
+/**
+ * Returns a byte array containing the current contents of the stream.
+ */
+public byte []
+toByteArray() {
+	byte [] out = new byte[pos];
+	System.arraycopy(array, 0, out, 0, pos);
+	return out;
+}
+
+}
diff --git a/src/org/xbill/DNS/DNSSEC.java b/src/org/xbill/DNS/DNSSEC.java
new file mode 100644
index 0000000..2707947
--- /dev/null
+++ b/src/org/xbill/DNS/DNSSEC.java
@@ -0,0 +1,1026 @@
+// Copyright (c) 1999-2010 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.math.*;
+import java.security.*;
+import java.security.interfaces.*;
+import java.security.spec.*;
+import java.util.*;
+
+/**
+ * Constants and methods relating to DNSSEC.
+ *
+ * DNSSEC provides authentication for DNS information.
+ * @see RRSIGRecord
+ * @see DNSKEYRecord
+ * @see RRset
+ *
+ * @author Brian Wellington
+ */
+
+public class DNSSEC {
+
+public static class Algorithm {
+	private Algorithm() {}
+
+	/** RSA/MD5 public key (deprecated) */
+	public static final int RSAMD5 = 1;
+
+	/** Diffie Hellman key */
+	public static final int DH = 2;
+
+	/** DSA public key */
+	public static final int DSA = 3;
+
+	/** RSA/SHA1 public key */
+	public static final int RSASHA1 = 5;
+
+	/** DSA/SHA1, NSEC3-aware public key */
+	public static final int DSA_NSEC3_SHA1 = 6;
+
+	/** RSA/SHA1, NSEC3-aware public key */
+	public static final int RSA_NSEC3_SHA1 = 7;
+
+	/** RSA/SHA256 public key */
+	public static final int RSASHA256 = 8;
+
+	/** RSA/SHA512 public key */
+	public static final int RSASHA512 = 10;
+
+	/** ECDSA Curve P-256 with SHA-256 public key **/
+	public static final int ECDSAP256SHA256 = 13;
+
+	/** ECDSA Curve P-384 with SHA-384 public key **/
+	public static final int ECDSAP384SHA384 = 14;
+
+	/** Indirect keys; the actual key is elsewhere. */
+	public static final int INDIRECT = 252;
+
+	/** Private algorithm, specified by domain name */
+	public static final int PRIVATEDNS = 253;
+
+	/** Private algorithm, specified by OID */
+	public static final int PRIVATEOID = 254;
+
+	private static Mnemonic algs = new Mnemonic("DNSSEC algorithm",
+						    Mnemonic.CASE_UPPER);
+
+	static {
+		algs.setMaximum(0xFF);
+		algs.setNumericAllowed(true);
+
+		algs.add(RSAMD5, "RSAMD5");
+		algs.add(DH, "DH");
+		algs.add(DSA, "DSA");
+		algs.add(RSASHA1, "RSASHA1");
+		algs.add(DSA_NSEC3_SHA1, "DSA-NSEC3-SHA1");
+		algs.add(RSA_NSEC3_SHA1, "RSA-NSEC3-SHA1");
+		algs.add(RSASHA256, "RSASHA256");
+		algs.add(RSASHA512, "RSASHA512");
+		algs.add(ECDSAP256SHA256, "ECDSAP256SHA256");
+		algs.add(ECDSAP384SHA384, "ECDSAP384SHA384");
+		algs.add(INDIRECT, "INDIRECT");
+		algs.add(PRIVATEDNS, "PRIVATEDNS");
+		algs.add(PRIVATEOID, "PRIVATEOID");
+	}
+
+	/**
+	 * Converts an algorithm into its textual representation
+	 */
+	public static String
+	string(int alg) {
+		return algs.getText(alg);
+	}
+
+	/**
+	 * Converts a textual representation of an algorithm into its numeric
+	 * code.  Integers in the range 0..255 are also accepted.
+	 * @param s The textual representation of the algorithm
+	 * @return The algorithm code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return algs.getValue(s);
+	}
+}
+
+private
+DNSSEC() { }
+
+private static void
+digestSIG(DNSOutput out, SIGBase sig) {
+	out.writeU16(sig.getTypeCovered());
+	out.writeU8(sig.getAlgorithm());
+	out.writeU8(sig.getLabels());
+	out.writeU32(sig.getOrigTTL());
+	out.writeU32(sig.getExpire().getTime() / 1000);
+	out.writeU32(sig.getTimeSigned().getTime() / 1000);
+	out.writeU16(sig.getFootprint());
+	sig.getSigner().toWireCanonical(out);
+}
+
+/**
+ * Creates a byte array containing the concatenation of the fields of the
+ * SIG record and the RRsets to be signed/verified.  This does not perform
+ * a cryptographic digest.
+ * @param rrsig The RRSIG record used to sign/verify the rrset.
+ * @param rrset The data to be signed/verified.
+ * @return The data to be cryptographically signed or verified.
+ */
+public static byte []
+digestRRset(RRSIGRecord rrsig, RRset rrset) {
+	DNSOutput out = new DNSOutput();
+	digestSIG(out, rrsig);
+
+	int size = rrset.size();
+	Record [] records = new Record[size];
+
+	Iterator it = rrset.rrs();
+	Name name = rrset.getName();
+	Name wild = null;
+	int sigLabels = rrsig.getLabels() + 1; // Add the root label back.
+	if (name.labels() > sigLabels)
+		wild = name.wild(name.labels() - sigLabels);
+	while (it.hasNext())
+		records[--size] = (Record) it.next();
+	Arrays.sort(records);
+
+	DNSOutput header = new DNSOutput();
+	if (wild != null)
+		wild.toWireCanonical(header);
+	else
+		name.toWireCanonical(header);
+	header.writeU16(rrset.getType());
+	header.writeU16(rrset.getDClass());
+	header.writeU32(rrsig.getOrigTTL());
+	for (int i = 0; i < records.length; i++) {
+		out.writeByteArray(header.toByteArray());
+		int lengthPosition = out.current();
+		out.writeU16(0);
+		out.writeByteArray(records[i].rdataToWireCanonical());
+		int rrlength = out.current() - lengthPosition - 2;
+		out.save();
+		out.jump(lengthPosition);
+		out.writeU16(rrlength);
+		out.restore();
+	}
+	return out.toByteArray();
+}
+
+/**
+ * Creates a byte array containing the concatenation of the fields of the
+ * SIG(0) record and the message to be signed.  This does not perform
+ * a cryptographic digest.
+ * @param sig The SIG record used to sign the rrset.
+ * @param msg The message to be signed.
+ * @param previous If this is a response, the signature from the query.
+ * @return The data to be cryptographically signed.
+ */
+public static byte []
+digestMessage(SIGRecord sig, Message msg, byte [] previous) {
+	DNSOutput out = new DNSOutput();
+	digestSIG(out, sig);
+
+	if (previous != null)
+		out.writeByteArray(previous);
+
+	msg.toWire(out);
+	return out.toByteArray();
+}
+
+/**
+ * A DNSSEC exception.
+ */
+public static class DNSSECException extends Exception {
+	DNSSECException(String s) {
+		super(s);
+	}
+}
+
+/**
+ * An algorithm is unsupported by this DNSSEC implementation.
+ */
+public static class UnsupportedAlgorithmException extends DNSSECException {
+	UnsupportedAlgorithmException(int alg) {
+		super("Unsupported algorithm: " + alg);
+	}
+}
+
+/**
+ * The cryptographic data in a DNSSEC key is malformed.
+ */
+public static class MalformedKeyException extends DNSSECException {
+	MalformedKeyException(KEYBase rec) {
+		super("Invalid key data: " + rec.rdataToString());
+	}
+}
+
+/**
+ * A DNSSEC verification failed because fields in the DNSKEY and RRSIG records
+ * do not match.
+ */
+public static class KeyMismatchException extends DNSSECException {
+	private KEYBase key;
+	private SIGBase sig;
+
+	KeyMismatchException(KEYBase key, SIGBase sig) {
+		super("key " +
+		      key.getName() + "/" +
+		      DNSSEC.Algorithm.string(key.getAlgorithm()) + "/" +
+		      key.getFootprint() + " " +
+		      "does not match signature " +
+		      sig.getSigner() + "/" +
+		      DNSSEC.Algorithm.string(sig.getAlgorithm()) + "/" +
+		      sig.getFootprint());
+	}
+}
+
+/**
+ * A DNSSEC verification failed because the signature has expired.
+ */
+public static class SignatureExpiredException extends DNSSECException {
+	private Date when, now;
+
+	SignatureExpiredException(Date when, Date now) {
+		super("signature expired");
+		this.when = when;
+		this.now = now;
+	}
+
+	/**
+	 * @return When the signature expired
+	 */
+	public Date
+	getExpiration() {
+		return when;
+	}
+
+	/**
+	 * @return When the verification was attempted
+	 */
+	public Date
+	getVerifyTime() {
+		return now;
+	}
+}
+
+/**
+ * A DNSSEC verification failed because the signature has not yet become valid.
+ */
+public static class SignatureNotYetValidException extends DNSSECException {
+	private Date when, now;
+
+	SignatureNotYetValidException(Date when, Date now) {
+		super("signature is not yet valid");
+		this.when = when;
+		this.now = now;
+	}
+
+	/**
+	 * @return When the signature will become valid
+	 */
+	public Date
+	getExpiration() {
+		return when;
+	}
+
+	/**
+	 * @return When the verification was attempted
+	 */
+	public Date
+	getVerifyTime() {
+		return now;
+	}
+}
+
+/**
+ * A DNSSEC verification failed because the cryptographic signature
+ * verification failed.
+ */
+public static class SignatureVerificationException extends DNSSECException {
+	SignatureVerificationException() {
+		super("signature verification failed");
+	}
+}
+
+/**
+ * The key data provided is inconsistent.
+ */
+public static class IncompatibleKeyException extends IllegalArgumentException {
+	IncompatibleKeyException() {
+		super("incompatible keys");
+	}
+}
+
+private static int
+BigIntegerLength(BigInteger i) {
+	return (i.bitLength() + 7) / 8;
+}
+
+private static BigInteger
+readBigInteger(DNSInput in, int len) throws IOException {
+	byte [] b = in.readByteArray(len);
+	return new BigInteger(1, b);
+}
+
+private static BigInteger
+readBigInteger(DNSInput in) {
+	byte [] b = in.readByteArray();
+	return new BigInteger(1, b);
+}
+
+private static void
+writeBigInteger(DNSOutput out, BigInteger val) {
+	byte [] b = val.toByteArray();
+	if (b[0] == 0)
+		out.writeByteArray(b, 1, b.length - 1);
+	else
+		out.writeByteArray(b);
+}
+
+private static PublicKey
+toRSAPublicKey(KEYBase r) throws IOException, GeneralSecurityException {
+	DNSInput in = new DNSInput(r.getKey());
+	int exponentLength = in.readU8();
+	if (exponentLength == 0)
+		exponentLength = in.readU16();
+	BigInteger exponent = readBigInteger(in, exponentLength);
+	BigInteger modulus = readBigInteger(in);
+
+	KeyFactory factory = KeyFactory.getInstance("RSA");
+	return factory.generatePublic(new RSAPublicKeySpec(modulus, exponent));
+}
+
+private static PublicKey
+toDSAPublicKey(KEYBase r) throws IOException, GeneralSecurityException,
+	MalformedKeyException
+{
+	DNSInput in = new DNSInput(r.getKey());
+
+	int t = in.readU8();
+	if (t > 8)
+		throw new MalformedKeyException(r);
+
+	BigInteger q = readBigInteger(in, 20);
+	BigInteger p = readBigInteger(in, 64 + t*8);
+	BigInteger g = readBigInteger(in, 64 + t*8);
+	BigInteger y = readBigInteger(in, 64 + t*8);
+
+	KeyFactory factory = KeyFactory.getInstance("DSA");
+	return factory.generatePublic(new DSAPublicKeySpec(y, p, q, g));
+}
+
+private static class ECKeyInfo {
+	int length;
+	public BigInteger p, a, b, gx, gy, n;
+	EllipticCurve curve;
+	ECParameterSpec spec;
+
+	ECKeyInfo(int length, String p_str, String a_str, String b_str,
+		  String gx_str, String gy_str, String n_str)
+	{
+		this.length = length;
+		p = new BigInteger(p_str, 16);
+		a = new BigInteger(a_str, 16);
+		b = new BigInteger(b_str, 16);
+		gx = new BigInteger(gx_str, 16);
+		gy = new BigInteger(gy_str, 16);
+		n = new BigInteger(n_str, 16);
+		curve = new EllipticCurve(new ECFieldFp(p), a, b);
+		spec = new ECParameterSpec(curve, new ECPoint(gx, gy), n, 1);
+	}
+}
+
+// RFC 5114 Section 2.6
+private static final ECKeyInfo ECDSA_P256 = new ECKeyInfo(32,
+	"FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFF",
+	"FFFFFFFF00000001000000000000000000000000FFFFFFFFFFFFFFFFFFFFFFFC",
+	"5AC635D8AA3A93E7B3EBBD55769886BC651D06B0CC53B0F63BCE3C3E27D2604B",
+	"6B17D1F2E12C4247F8BCE6E563A440F277037D812DEB33A0F4A13945D898C296",
+	"4FE342E2FE1A7F9B8EE7EB4A7C0F9E162BCE33576B315ECECBB6406837BF51F5",
+	"FFFFFFFF00000000FFFFFFFFFFFFFFFFBCE6FAADA7179E84F3B9CAC2FC632551");
+
+// RFC 5114 Section 2.7
+private static final ECKeyInfo ECDSA_P384 = new ECKeyInfo(48,
+	"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFF",
+	"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFFFF0000000000000000FFFFFFFC",
+	"B3312FA7E23EE7E4988E056BE3F82D19181D9C6EFE8141120314088F5013875AC656398D8A2ED19D2A85C8EDD3EC2AEF",
+	"AA87CA22BE8B05378EB1C71EF320AD746E1D3B628BA79B9859F741E082542A385502F25DBF55296C3A545E3872760AB7",
+	"3617DE4A96262C6F5D9E98BF9292DC29F8F41DBD289A147CE9DA3113B5F0B8C00A60B1CE1D7E819D7A431D7C90EA0E5F",
+	"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFC7634D81F4372DDF581A0DB248B0A77AECEC196ACCC52973");
+
+private static PublicKey
+toECDSAPublicKey(KEYBase r, ECKeyInfo keyinfo) throws IOException,
+	GeneralSecurityException, MalformedKeyException
+{
+	DNSInput in = new DNSInput(r.getKey());
+
+	// RFC 6605 Section 4
+	BigInteger x = readBigInteger(in, keyinfo.length);
+	BigInteger y = readBigInteger(in, keyinfo.length);
+	ECPoint q = new ECPoint(x, y);
+
+	KeyFactory factory = KeyFactory.getInstance("EC");
+	return factory.generatePublic(new ECPublicKeySpec(q, keyinfo.spec));
+}
+
+/** Converts a KEY/DNSKEY record into a PublicKey */
+static PublicKey
+toPublicKey(KEYBase r) throws DNSSECException {
+	int alg = r.getAlgorithm();
+	try {
+		switch (alg) {
+		case Algorithm.RSAMD5:
+		case Algorithm.RSASHA1:
+		case Algorithm.RSA_NSEC3_SHA1:
+		case Algorithm.RSASHA256:
+		case Algorithm.RSASHA512:
+			return toRSAPublicKey(r);
+		case Algorithm.DSA:
+		case Algorithm.DSA_NSEC3_SHA1:
+			return toDSAPublicKey(r);
+		case Algorithm.ECDSAP256SHA256:
+			return toECDSAPublicKey(r, ECDSA_P256);
+		case Algorithm.ECDSAP384SHA384:
+			return toECDSAPublicKey(r, ECDSA_P384);
+		default:
+			throw new UnsupportedAlgorithmException(alg);
+		}
+	}
+	catch (IOException e) {
+		throw new MalformedKeyException(r);
+	}
+	catch (GeneralSecurityException e) {
+		throw new DNSSECException(e.toString());
+	}
+}
+
+private static byte []
+fromRSAPublicKey(RSAPublicKey key) {
+	DNSOutput out = new DNSOutput();
+	BigInteger exponent = key.getPublicExponent();
+	BigInteger modulus = key.getModulus();
+	int exponentLength = BigIntegerLength(exponent);
+
+	if (exponentLength < 256)
+		out.writeU8(exponentLength);
+	else {
+		out.writeU8(0);
+		out.writeU16(exponentLength);
+	}
+	writeBigInteger(out, exponent);
+	writeBigInteger(out, modulus);
+
+	return out.toByteArray();
+}
+
+private static byte []
+fromDSAPublicKey(DSAPublicKey key) {
+	DNSOutput out = new DNSOutput();
+	BigInteger q = key.getParams().getQ();
+	BigInteger p = key.getParams().getP();
+	BigInteger g = key.getParams().getG();
+	BigInteger y = key.getY();
+	int t = (p.toByteArray().length - 64) / 8;
+
+	out.writeU8(t);
+	writeBigInteger(out, q);
+	writeBigInteger(out, p);
+	writeBigInteger(out, g);
+	writeBigInteger(out, y);
+
+	return out.toByteArray();
+}
+
+private static byte []
+fromECDSAPublicKey(ECPublicKey key) {
+	DNSOutput out = new DNSOutput();
+
+	BigInteger x = key.getW().getAffineX();
+	BigInteger y = key.getW().getAffineY();
+
+	writeBigInteger(out, x);
+	writeBigInteger(out, y);
+
+	return out.toByteArray();
+}
+
+/** Builds a DNSKEY record from a PublicKey */
+static byte []
+fromPublicKey(PublicKey key, int alg) throws DNSSECException
+{
+
+	switch (alg) {
+	case Algorithm.RSAMD5:
+	case Algorithm.RSASHA1:
+	case Algorithm.RSA_NSEC3_SHA1:
+	case Algorithm.RSASHA256:
+	case Algorithm.RSASHA512:
+		if (! (key instanceof RSAPublicKey))
+			throw new IncompatibleKeyException();
+		return fromRSAPublicKey((RSAPublicKey) key);
+	case Algorithm.DSA:
+	case Algorithm.DSA_NSEC3_SHA1:
+		if (! (key instanceof DSAPublicKey))
+			throw new IncompatibleKeyException();
+		return fromDSAPublicKey((DSAPublicKey) key);
+	case Algorithm.ECDSAP256SHA256:
+	case Algorithm.ECDSAP384SHA384:
+		if (! (key instanceof ECPublicKey))
+			throw new IncompatibleKeyException();
+		return fromECDSAPublicKey((ECPublicKey) key);
+	default:
+		throw new UnsupportedAlgorithmException(alg);
+	}
+}
+
+/**
+ * Convert an algorithm number to the corresponding JCA string.
+ * @param alg The algorithm number.
+ * @throws UnsupportedAlgorithmException The algorithm is unknown.
+ */
+public static String
+algString(int alg) throws UnsupportedAlgorithmException {
+	switch (alg) {
+	case Algorithm.RSAMD5:
+		return "MD5withRSA";
+	case Algorithm.DSA:
+	case Algorithm.DSA_NSEC3_SHA1:
+		return "SHA1withDSA";
+	case Algorithm.RSASHA1:
+	case Algorithm.RSA_NSEC3_SHA1:
+		return "SHA1withRSA";
+	case Algorithm.RSASHA256:
+		return "SHA256withRSA";
+	case Algorithm.RSASHA512:
+		return "SHA512withRSA";
+	case Algorithm.ECDSAP256SHA256:
+		return "SHA256withECDSA";
+	case Algorithm.ECDSAP384SHA384:
+		return "SHA384withECDSA";
+	default:
+		throw new UnsupportedAlgorithmException(alg);
+	}
+}
+
+private static final int ASN1_SEQ = 0x30;
+private static final int ASN1_INT = 0x2;
+
+private static final int DSA_LEN = 20;
+
+private static byte []
+DSASignaturefromDNS(byte [] dns) throws DNSSECException, IOException {
+	if (dns.length != 1 + DSA_LEN * 2)
+		throw new SignatureVerificationException();
+
+	DNSInput in = new DNSInput(dns);
+	DNSOutput out = new DNSOutput();
+
+	int t = in.readU8();
+
+	byte [] r = in.readByteArray(DSA_LEN);
+	int rlen = DSA_LEN;
+	if (r[0] < 0)
+		rlen++;
+
+	byte [] s = in.readByteArray(DSA_LEN);
+        int slen = DSA_LEN;
+        if (s[0] < 0)
+                slen++;
+
+	out.writeU8(ASN1_SEQ);
+	out.writeU8(rlen + slen + 4);
+
+	out.writeU8(ASN1_INT);
+	out.writeU8(rlen);
+	if (rlen > DSA_LEN)
+		out.writeU8(0);
+	out.writeByteArray(r);
+
+	out.writeU8(ASN1_INT);
+	out.writeU8(slen);
+	if (slen > DSA_LEN)
+		out.writeU8(0);
+	out.writeByteArray(s);
+
+	return out.toByteArray();
+}
+
+private static byte []
+DSASignaturetoDNS(byte [] signature, int t) throws IOException {
+	DNSInput in = new DNSInput(signature);
+	DNSOutput out = new DNSOutput();
+
+	out.writeU8(t);
+
+	int tmp = in.readU8();
+	if (tmp != ASN1_SEQ)
+		throw new IOException();
+	int seqlen = in.readU8();
+
+	tmp = in.readU8();
+	if (tmp != ASN1_INT)
+		throw new IOException();
+	int rlen = in.readU8();
+	if (rlen == DSA_LEN + 1) {
+		if (in.readU8() != 0)
+			throw new IOException();
+	} else if (rlen != DSA_LEN)
+		throw new IOException();
+	byte [] bytes = in.readByteArray(DSA_LEN);
+	out.writeByteArray(bytes);
+
+	tmp = in.readU8();
+	if (tmp != ASN1_INT)
+		throw new IOException();
+	int slen = in.readU8();
+	if (slen == DSA_LEN + 1) {
+		if (in.readU8() != 0)
+			throw new IOException();
+	} else if (slen != DSA_LEN)
+		throw new IOException();
+	bytes = in.readByteArray(DSA_LEN);
+	out.writeByteArray(bytes);
+
+	return out.toByteArray();
+}
+
+private static byte []
+ECDSASignaturefromDNS(byte [] signature, ECKeyInfo keyinfo)
+	throws DNSSECException, IOException
+{
+	if (signature.length != keyinfo.length * 2)
+		throw new SignatureVerificationException();
+
+	DNSInput in = new DNSInput(signature);
+	DNSOutput out = new DNSOutput();
+
+	byte [] r = in.readByteArray(keyinfo.length);
+	int rlen = keyinfo.length;
+	if (r[0] < 0)
+		rlen++;
+
+	byte [] s = in.readByteArray(keyinfo.length);
+	int slen = keyinfo.length;
+	if (s[0] < 0)
+		slen++;
+
+	out.writeU8(ASN1_SEQ);
+	out.writeU8(rlen + slen + 4);
+
+	out.writeU8(ASN1_INT);
+	out.writeU8(rlen);
+	if (rlen > keyinfo.length)
+		out.writeU8(0);
+	out.writeByteArray(r);
+
+	out.writeU8(ASN1_INT);
+	out.writeU8(slen);
+	if (slen > keyinfo.length)
+		out.writeU8(0);
+	out.writeByteArray(s);
+
+	return out.toByteArray();
+}
+
+private static byte []
+ECDSASignaturetoDNS(byte [] signature, ECKeyInfo keyinfo) throws IOException {
+	DNSInput in = new DNSInput(signature);
+	DNSOutput out = new DNSOutput();
+
+	int tmp = in.readU8();
+	if (tmp != ASN1_SEQ)
+		throw new IOException();
+	int seqlen = in.readU8();
+
+	tmp = in.readU8();
+	if (tmp != ASN1_INT)
+		throw new IOException();
+	int rlen = in.readU8();
+	if (rlen == keyinfo.length + 1) {
+		if (in.readU8() != 0)
+			throw new IOException();
+	} else if (rlen != keyinfo.length)
+		throw new IOException();
+	byte[] bytes = in.readByteArray(keyinfo.length);
+	out.writeByteArray(bytes);
+
+	tmp = in.readU8();
+	if (tmp != ASN1_INT)
+		throw new IOException();
+	int slen = in.readU8();
+	if (slen == keyinfo.length + 1) {
+		if (in.readU8() != 0)
+			throw new IOException();
+	} else if (slen != keyinfo.length)
+		throw new IOException();
+	bytes = in.readByteArray(keyinfo.length);
+	out.writeByteArray(bytes);
+
+	return out.toByteArray();
+}
+
+private static void
+verify(PublicKey key, int alg, byte [] data, byte [] signature)
+throws DNSSECException
+{
+	if (key instanceof DSAPublicKey) {
+		try {
+			signature = DSASignaturefromDNS(signature);
+		}
+		catch (IOException e) {
+			throw new IllegalStateException();
+		}
+	} else if (key instanceof ECPublicKey) {
+		try {
+			switch (alg) {
+			case Algorithm.ECDSAP256SHA256:
+				signature = ECDSASignaturefromDNS(signature,
+								  ECDSA_P256);
+				break;
+			case Algorithm.ECDSAP384SHA384:
+				signature = ECDSASignaturefromDNS(signature,
+								  ECDSA_P384);
+				break;
+			default:
+				throw new UnsupportedAlgorithmException(alg);
+			}
+		}
+		catch (IOException e) {
+			throw new IllegalStateException();
+		}
+	}
+
+	try {
+		Signature s = Signature.getInstance(algString(alg));
+		s.initVerify(key);
+		s.update(data);
+		if (!s.verify(signature))
+			throw new SignatureVerificationException();
+	}
+	catch (GeneralSecurityException e) {
+		throw new DNSSECException(e.toString());
+	}
+}
+
+private static boolean
+matches(SIGBase sig, KEYBase key)
+{
+	return (key.getAlgorithm() == sig.getAlgorithm() &&
+		key.getFootprint() == sig.getFootprint() &&
+		key.getName().equals(sig.getSigner()));
+}
+
+/**
+ * Verify a DNSSEC signature.
+ * @param rrset The data to be verified.
+ * @param rrsig The RRSIG record containing the signature.
+ * @param key The DNSKEY record to verify the signature with.
+ * @throws UnsupportedAlgorithmException The algorithm is unknown
+ * @throws MalformedKeyException The key is malformed
+ * @throws KeyMismatchException The key and signature do not match
+ * @throws SignatureExpiredException The signature has expired
+ * @throws SignatureNotYetValidException The signature is not yet valid
+ * @throws SignatureVerificationException The signature does not verify.
+ * @throws DNSSECException Some other error occurred.
+ */
+public static void
+verify(RRset rrset, RRSIGRecord rrsig, DNSKEYRecord key) throws DNSSECException
+{
+	if (!matches(rrsig, key))
+		throw new KeyMismatchException(key, rrsig);
+
+	Date now = new Date();
+	if (now.compareTo(rrsig.getExpire()) > 0)
+		throw new SignatureExpiredException(rrsig.getExpire(), now);
+	if (now.compareTo(rrsig.getTimeSigned()) < 0)
+		throw new SignatureNotYetValidException(rrsig.getTimeSigned(),
+							now);
+
+	verify(key.getPublicKey(), rrsig.getAlgorithm(),
+	       digestRRset(rrsig, rrset), rrsig.getSignature());
+}
+
+private static byte []
+sign(PrivateKey privkey, PublicKey pubkey, int alg, byte [] data,
+     String provider) throws DNSSECException
+{
+	byte [] signature;
+	try {
+		Signature s;
+		if (provider != null)
+			s = Signature.getInstance(algString(alg), provider);
+		else
+			s = Signature.getInstance(algString(alg));
+		s.initSign(privkey);
+		s.update(data);
+		signature = s.sign();
+	}
+	catch (GeneralSecurityException e) {
+		throw new DNSSECException(e.toString());
+	}
+
+	if (pubkey instanceof DSAPublicKey) {
+		try {
+			DSAPublicKey dsa = (DSAPublicKey) pubkey;
+			BigInteger P = dsa.getParams().getP();
+			int t = (BigIntegerLength(P) - 64) / 8;
+			signature = DSASignaturetoDNS(signature, t);
+		}
+		catch (IOException e) {
+			throw new IllegalStateException();
+		}
+	} else if (pubkey instanceof ECPublicKey) {
+		try {
+			switch (alg) {
+			case Algorithm.ECDSAP256SHA256:
+				signature = ECDSASignaturetoDNS(signature,
+								ECDSA_P256);
+				break;
+			case Algorithm.ECDSAP384SHA384:
+				signature = ECDSASignaturetoDNS(signature,
+								ECDSA_P384);
+				break;
+			default:
+				throw new UnsupportedAlgorithmException(alg);
+			}
+		}
+		catch (IOException e) {
+			throw new IllegalStateException();
+		}
+	}
+
+	return signature;
+}
+static void
+checkAlgorithm(PrivateKey key, int alg) throws UnsupportedAlgorithmException
+{
+	switch (alg) {
+	case Algorithm.RSAMD5:
+	case Algorithm.RSASHA1:
+	case Algorithm.RSA_NSEC3_SHA1:
+	case Algorithm.RSASHA256:
+	case Algorithm.RSASHA512:
+		if (! (key instanceof RSAPrivateKey))
+			throw new IncompatibleKeyException();
+		break;
+	case Algorithm.DSA:
+	case Algorithm.DSA_NSEC3_SHA1:
+		if (! (key instanceof DSAPrivateKey))
+			throw new IncompatibleKeyException();
+		break;
+	case Algorithm.ECDSAP256SHA256:
+	case Algorithm.ECDSAP384SHA384:
+		if (! (key instanceof ECPrivateKey))
+			throw new IncompatibleKeyException();
+		break;
+	default:
+		throw new UnsupportedAlgorithmException(alg);
+	}
+}
+
+/**
+ * Generate a DNSSEC signature.  key and privateKey must refer to the
+ * same underlying cryptographic key.
+ * @param rrset The data to be signed
+ * @param key The DNSKEY record to use as part of signing
+ * @param privkey The PrivateKey to use when signing
+ * @param inception The time at which the signatures should become valid
+ * @param expiration The time at which the signatures should expire
+ * @throws UnsupportedAlgorithmException The algorithm is unknown
+ * @throws MalformedKeyException The key is malformed
+ * @throws DNSSECException Some other error occurred.
+ * @return The generated signature
+ */
+public static RRSIGRecord
+sign(RRset rrset, DNSKEYRecord key, PrivateKey privkey,
+     Date inception, Date expiration) throws DNSSECException
+{
+	return sign(rrset, key, privkey, inception, expiration, null);
+}
+
+/**
+ * Generate a DNSSEC signature.  key and privateKey must refer to the
+ * same underlying cryptographic key.
+ * @param rrset The data to be signed
+ * @param key The DNSKEY record to use as part of signing
+ * @param privkey The PrivateKey to use when signing
+ * @param inception The time at which the signatures should become valid
+ * @param expiration The time at which the signatures should expire
+ * @param provider The name of the JCA provider.  If non-null, it will be
+ * passed to JCA getInstance() methods.
+ * @throws UnsupportedAlgorithmException The algorithm is unknown
+ * @throws MalformedKeyException The key is malformed
+ * @throws DNSSECException Some other error occurred.
+ * @return The generated signature
+ */
+public static RRSIGRecord
+sign(RRset rrset, DNSKEYRecord key, PrivateKey privkey,
+     Date inception, Date expiration, String provider) throws DNSSECException
+{
+	int alg = key.getAlgorithm();
+	checkAlgorithm(privkey, alg);
+
+	RRSIGRecord rrsig = new RRSIGRecord(rrset.getName(), rrset.getDClass(),
+					    rrset.getTTL(), rrset.getType(),
+					    alg, rrset.getTTL(),
+					    expiration, inception,
+					    key.getFootprint(),
+					    key.getName(), null);
+
+	rrsig.setSignature(sign(privkey, key.getPublicKey(), alg,
+				digestRRset(rrsig, rrset), provider));
+	return rrsig;
+}
+
+static SIGRecord
+signMessage(Message message, SIGRecord previous, KEYRecord key,
+	    PrivateKey privkey, Date inception, Date expiration)
+	throws DNSSECException
+{
+	int alg = key.getAlgorithm();
+	checkAlgorithm(privkey, alg);
+
+	SIGRecord sig = new SIGRecord(Name.root, DClass.ANY, 0, 0,
+					    alg, 0, expiration, inception,
+					    key.getFootprint(),
+					    key.getName(), null);
+	DNSOutput out = new DNSOutput();
+	digestSIG(out, sig);
+	if (previous != null)
+		out.writeByteArray(previous.getSignature());
+	message.toWire(out);
+
+	sig.setSignature(sign(privkey, key.getPublicKey(),
+			      alg, out.toByteArray(), null));
+	return sig;
+}
+
+static void
+verifyMessage(Message message, byte [] bytes, SIGRecord sig, SIGRecord previous,
+	      KEYRecord key) throws DNSSECException
+{
+	if (!matches(sig, key))
+		throw new KeyMismatchException(key, sig);
+
+	Date now = new Date();
+
+	if (now.compareTo(sig.getExpire()) > 0)
+		throw new SignatureExpiredException(sig.getExpire(), now);
+	if (now.compareTo(sig.getTimeSigned()) < 0)
+		throw new SignatureNotYetValidException(sig.getTimeSigned(),
+							now);
+
+	DNSOutput out = new DNSOutput();
+	digestSIG(out, sig);
+	if (previous != null)
+		out.writeByteArray(previous.getSignature());
+
+	Header header = (Header) message.getHeader().clone();
+	header.decCount(Section.ADDITIONAL);
+	out.writeByteArray(header.toWire());
+
+	out.writeByteArray(bytes, Header.LENGTH,
+			   message.sig0start - Header.LENGTH);
+
+	verify(key.getPublicKey(), sig.getAlgorithm(),
+	       out.toByteArray(), sig.getSignature());
+}
+
+/**
+ * Generate the digest value for a DS key
+ * @param key Which is covered by the DS record
+ * @param digestid The type of digest
+ * @return The digest value as an array of bytes
+ */
+static byte []
+generateDSDigest(DNSKEYRecord key, int digestid)
+{
+	MessageDigest digest;
+	try {
+		switch (digestid) {
+		case DSRecord.Digest.SHA1:
+			digest = MessageDigest.getInstance("sha-1");
+			break;
+		case DSRecord.Digest.SHA256:
+			digest = MessageDigest.getInstance("sha-256");
+			break;
+		case DSRecord.Digest.SHA384:
+			digest = MessageDigest.getInstance("sha-384");
+			break;
+		default:
+			throw new IllegalArgumentException(
+					"unknown DS digest type " + digestid);
+		}
+	}
+	catch (NoSuchAlgorithmException e) {
+		throw new IllegalStateException("no message digest support");
+	}
+	digest.update(key.getName().toWire());
+	digest.update(key.rdataToWireCanonical());
+	return digest.digest();
+}
+
+}
diff --git a/src/org/xbill/DNS/DSRecord.java b/src/org/xbill/DNS/DSRecord.java
new file mode 100644
index 0000000..4c1ebce
--- /dev/null
+++ b/src/org/xbill/DNS/DSRecord.java
@@ -0,0 +1,157 @@
+// Copyright (c) 2002-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * DS - contains a Delegation Signer record, which acts as a
+ * placeholder for KEY records in the parent zone.
+ * @see DNSSEC
+ *
+ * @author David Blacka
+ * @author Brian Wellington
+ */
+
+public class DSRecord extends Record {
+
+public static class Digest {
+	private Digest() {}
+
+	/** SHA-1 */
+	public static final int SHA1 = 1;
+
+	/** SHA-256 */
+	public static final int SHA256 = 2;
+
+	/** SHA-384 */
+	public static final int SHA384 = 4;
+}
+
+public static final int SHA1_DIGEST_ID = Digest.SHA1;
+public static final int SHA256_DIGEST_ID = Digest.SHA256;
+public static final int SHA384_DIGEST_ID = Digest.SHA384;
+
+private static final long serialVersionUID = -9001819329700081493L;
+
+private int footprint;
+private int alg;
+private int digestid;
+private byte [] digest;
+
+DSRecord() {}
+
+Record
+getObject() {
+	return new DSRecord();
+}
+
+/**
+ * Creates a DS Record from the given data
+ * @param footprint The original KEY record's footprint (keyid).
+ * @param alg The original key algorithm.
+ * @param digestid The digest id code.
+ * @param digest A hash of the original key.
+ */
+public
+DSRecord(Name name, int dclass, long ttl, int footprint, int alg,
+	 int digestid, byte [] digest)
+{
+	super(name, Type.DS, dclass, ttl);
+	this.footprint = checkU16("footprint", footprint);
+	this.alg = checkU8("alg", alg);
+	this.digestid = checkU8("digestid", digestid);
+	this.digest = digest;
+}
+
+/**
+ * Creates a DS Record from the given data
+ * @param digestid The digest id code.
+ * @param key The key to digest
+ */
+public
+DSRecord(Name name, int dclass, long ttl, int digestid, DNSKEYRecord key)
+{
+	this(name, dclass, ttl, key.getFootprint(), key.getAlgorithm(),
+	     digestid, DNSSEC.generateDSDigest(key, digestid));
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	footprint = in.readU16();
+	alg = in.readU8();
+	digestid = in.readU8();
+	digest = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	footprint = st.getUInt16();
+	alg = st.getUInt8();
+	digestid = st.getUInt8();
+	digest = st.getHex();
+}
+
+/**
+ * Converts rdata to a String
+ */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(footprint);
+	sb.append(" ");
+	sb.append(alg);
+	sb.append(" ");
+	sb.append(digestid);
+	if (digest != null) {
+		sb.append(" ");
+		sb.append(base16.toString(digest));
+	}
+
+	return sb.toString();
+}
+
+/**
+ * Returns the key's algorithm.
+ */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ *  Returns the key's Digest ID.
+ */
+public int
+getDigestID()
+{
+	return digestid;
+}
+  
+/**
+ * Returns the binary hash of the key.
+ */
+public byte []
+getDigest() {
+	return digest;
+}
+
+/**
+ * Returns the key's footprint.
+ */
+public int
+getFootprint() {
+	return footprint;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(footprint);
+	out.writeU8(alg);
+	out.writeU8(digestid);
+	if (digest != null)
+		out.writeByteArray(digest);
+}
+
+}
diff --git a/src/org/xbill/DNS/EDNSOption.java b/src/org/xbill/DNS/EDNSOption.java
new file mode 100644
index 0000000..a65bd19
--- /dev/null
+++ b/src/org/xbill/DNS/EDNSOption.java
@@ -0,0 +1,215 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.Arrays;
+
+/**
+ * DNS extension options, as described in RFC 2671.  The rdata of an OPT record
+ * is defined as a list of options; this represents a single option.
+ * 
+ * @author Brian Wellington
+ * @author Ming Zhou &lt;mizhou@bnivideo.com&gt;, Beaumaris Networks
+ */
+public abstract class EDNSOption {
+
+public static class Code {
+	private Code() {}
+
+	/** Name Server Identifier, RFC 5001 */
+	public final static int NSID = 3;
+
+	/** Client Subnet, defined in draft-vandergaast-edns-client-subnet-00 */
+	public final static int CLIENT_SUBNET = 20730;
+
+	private static Mnemonic codes = new Mnemonic("EDNS Option Codes",
+						     Mnemonic.CASE_UPPER);
+
+	static {
+		codes.setMaximum(0xFFFF);
+		codes.setPrefix("CODE");
+		codes.setNumericAllowed(true);
+
+		codes.add(NSID, "NSID");
+		codes.add(CLIENT_SUBNET, "CLIENT_SUBNET");
+	}
+
+	/**
+	 * Converts an EDNS Option Code into its textual representation
+	 */
+	public static String
+	string(int code) {
+		return codes.getText(code);
+	}
+
+	/**
+	 * Converts a textual representation of an EDNS Option Code into its
+	 * numeric value.
+	 * @param s The textual representation of the option code
+	 * @return The option code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return codes.getValue(s);
+	}
+}
+
+private final int code;
+
+/**
+ * 
+ * Creates an option with the given option code and data.
+ */
+public 
+EDNSOption(int code) {
+	this.code = Record.checkU16("code", code);
+}
+
+public String 
+toString() {
+	StringBuffer sb = new StringBuffer();
+
+	sb.append("{");
+	sb.append(EDNSOption.Code.string(code));
+	sb.append(": ");
+	sb.append(optionToString());
+	sb.append("}");
+
+	return sb.toString();
+}
+
+/**
+ * Returns the EDNS Option's code.
+ *
+ * @return the option code
+ */
+public int 
+getCode() {
+	return code;
+}
+
+/**
+ * Returns the EDNS Option's data, as a byte array.
+ * 
+ * @return the option data
+ */
+byte [] 
+getData() {
+	DNSOutput out = new DNSOutput();
+	optionToWire(out);
+	return out.toByteArray();
+}
+
+/**
+ * Converts the wire format of an EDNS Option (the option data only) into the
+ * type-specific format.
+ * @param in The input Stream.
+ */
+abstract void 
+optionFromWire(DNSInput in) throws IOException;
+
+/**
+ * Converts the wire format of an EDNS Option (including code and length) into
+ * the type-specific format.
+ * @param out The input stream.
+ */
+static EDNSOption
+fromWire(DNSInput in) throws IOException {
+	int code, length;
+
+	code = in.readU16();
+	length = in.readU16();
+	if (in.remaining() < length)
+		throw new WireParseException("truncated option");
+	int save = in.saveActive();
+	in.setActive(length);
+	EDNSOption option;
+	switch (code) {
+	case Code.NSID:
+		option = new NSIDOption();
+		break;
+	case Code.CLIENT_SUBNET:
+		option = new ClientSubnetOption();
+		break;
+	default:
+		option = new GenericEDNSOption(code);
+		break;
+	}
+	option.optionFromWire(in);
+	in.restoreActive(save);
+
+	return option;
+}
+
+/**
+ * Converts the wire format of an EDNS Option (including code and length) into
+ * the type-specific format.
+ * @return The option, in wire format.
+ */
+public static EDNSOption
+fromWire(byte [] b) throws IOException {
+	return fromWire(new DNSInput(b));
+}
+
+/**
+ * Converts an EDNS Option (the type-specific option data only) into wire format.
+ * @param out The output stream.
+ */
+abstract void 
+optionToWire(DNSOutput out);
+
+/**
+ * Converts an EDNS Option (including code and length) into wire format.
+ * @param out The output stream.
+ */
+void
+toWire(DNSOutput out) {
+	out.writeU16(code);
+	int lengthPosition = out.current();
+	out.writeU16(0); /* until we know better */
+	optionToWire(out);
+	int length = out.current() - lengthPosition - 2;
+	out.writeU16At(length, lengthPosition);
+}
+
+/**
+ * Converts an EDNS Option (including code and length) into wire format.
+ * @return The option, in wire format.
+ */
+public byte []
+toWire() throws IOException {
+	DNSOutput out = new DNSOutput();
+	toWire(out);
+	return out.toByteArray();
+}
+
+/**
+ * Determines if two EDNS Options are identical.
+ * @param arg The option to compare to
+ * @return true if the options are equal, false otherwise.
+ */
+public boolean
+equals(Object arg) {
+	if (arg == null || !(arg instanceof EDNSOption))
+		return false;
+	EDNSOption opt = (EDNSOption) arg;
+	if (code != opt.code)
+		return false;
+	return Arrays.equals(getData(), opt.getData());
+}
+
+/**
+ * Generates a hash code based on the EDNS Option's data.
+ */
+public int
+hashCode() {
+	byte [] array = getData();
+	int hashval = 0;
+	for (int i = 0; i < array.length; i++)
+		hashval += ((hashval << 3) + (array[i] & 0xFF));
+	return hashval;
+}
+
+abstract String optionToString();
+
+}
diff --git a/src/org/xbill/DNS/EmptyRecord.java b/src/org/xbill/DNS/EmptyRecord.java
new file mode 100644
index 0000000..f5e61e8
--- /dev/null
+++ b/src/org/xbill/DNS/EmptyRecord.java
@@ -0,0 +1,42 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * A class implementing Records with no data; that is, records used in
+ * the question section of messages and meta-records in dynamic update.
+ *
+ * @author Brian Wellington
+ */
+
+class EmptyRecord extends Record {
+
+private static final long serialVersionUID = 3601852050646429582L;
+
+EmptyRecord() {}
+
+Record
+getObject() {
+	return new EmptyRecord();
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+}
+
+String
+rrToString() {
+	return "";
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+}
+
+}
diff --git a/src/org/xbill/DNS/ExtendedFlags.java b/src/org/xbill/DNS/ExtendedFlags.java
new file mode 100644
index 0000000..8f3bbab
--- /dev/null
+++ b/src/org/xbill/DNS/ExtendedFlags.java
@@ -0,0 +1,45 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to EDNS flags.
+ *
+ * @author Brian Wellington
+ */
+
+public final class ExtendedFlags {
+
+private static Mnemonic extflags = new Mnemonic("EDNS Flag",
+						Mnemonic.CASE_LOWER);
+
+/** dnssec ok */
+public static final int DO		= 0x8000;
+
+static {
+	extflags.setMaximum(0xFFFF);
+	extflags.setPrefix("FLAG");
+	extflags.setNumericAllowed(true);
+
+	extflags.add(DO, "do");
+}
+
+private
+ExtendedFlags() {}
+
+/** Converts a numeric extended flag into a String */
+public static String
+string(int i) {
+	return extflags.getText(i);
+}
+
+/**
+ * Converts a textual representation of an extended flag into its numeric
+ * value
+ */
+public static int
+value(String s) {
+	return extflags.getValue(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/ExtendedResolver.java b/src/org/xbill/DNS/ExtendedResolver.java
new file mode 100644
index 0000000..f762b84
--- /dev/null
+++ b/src/org/xbill/DNS/ExtendedResolver.java
@@ -0,0 +1,419 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+import java.io.*;
+import java.net.*;
+
+/**
+ * An implementation of Resolver that can send queries to multiple servers,
+ * sending the queries multiple times if necessary.
+ * @see Resolver
+ *
+ * @author Brian Wellington
+ */
+
+public class ExtendedResolver implements Resolver {
+
+private static class Resolution implements ResolverListener {
+	Resolver [] resolvers;
+	int [] sent;
+	Object [] inprogress;
+	int retries;
+	int outstanding;
+	boolean done;
+	Message query;
+	Message response;
+	Throwable thrown;
+	ResolverListener listener;
+
+	public
+	Resolution(ExtendedResolver eres, Message query) {
+		List l = eres.resolvers;
+		resolvers = (Resolver []) l.toArray (new Resolver[l.size()]);
+		if (eres.loadBalance) {
+			int nresolvers = resolvers.length;
+			/*
+			 * Note: this is not synchronized, since the
+			 * worst thing that can happen is a random
+			 * ordering, which is ok.
+			 */
+			int start = eres.lbStart++ % nresolvers;
+			if (eres.lbStart > nresolvers)
+				eres.lbStart %= nresolvers;
+			if (start > 0) {
+				Resolver [] shuffle = new Resolver[nresolvers];
+				for (int i = 0; i < nresolvers; i++) {
+					int pos = (i + start) % nresolvers;
+					shuffle[i] = resolvers[pos];
+				}
+				resolvers = shuffle;
+			}
+		}
+		sent = new int[resolvers.length];
+		inprogress = new Object[resolvers.length];
+		retries = eres.retries;
+		this.query = query;
+	}
+
+	/* Asynchronously sends a message. */
+	public void
+	send(int n) {
+		sent[n]++;
+		outstanding++;
+		try {
+			inprogress[n] = resolvers[n].sendAsync(query, this);
+		}
+		catch (Throwable t) {
+			synchronized (this) {
+				thrown = t;
+				done = true;
+				if (listener == null) {
+					notifyAll();
+					return;
+				}
+			}
+		}
+	}
+
+	/* Start a synchronous resolution */
+	public Message
+	start() throws IOException {
+		try {
+			/*
+			 * First, try sending synchronously.  If this works,
+			 * we're done.  Otherwise, we'll get an exception
+			 * and continue.  It would be easier to call send(0),
+			 * but this avoids a thread creation.  If and when
+			 * SimpleResolver.sendAsync() can be made to not
+			 * create a thread, this could be changed.
+			 */
+			sent[0]++;
+			outstanding++;
+			inprogress[0] = new Object();
+			return resolvers[0].send(query);
+		}
+		catch (Exception e) {
+			/*
+			 * This will either cause more queries to be sent
+			 * asynchronously or will set the 'done' flag.
+			 */
+			handleException(inprogress[0], e);
+		}
+		/*
+		 * Wait for a successful response or for each
+		 * subresolver to fail.
+		 */
+		synchronized (this) {
+			while (!done) {
+				try {
+					wait();
+				}
+				catch (InterruptedException e) {
+				}
+			}
+		}
+		/* Return the response or throw an exception */
+		if (response != null)
+			return response;
+		else if (thrown instanceof IOException)
+			throw (IOException) thrown;
+		else if (thrown instanceof RuntimeException)
+			throw (RuntimeException) thrown;
+		else if (thrown instanceof Error)
+			throw (Error) thrown;
+		else
+			throw new IllegalStateException
+				("ExtendedResolver failure");
+	}
+
+	/* Start an asynchronous resolution */
+	public void
+	startAsync(ResolverListener listener) {
+		this.listener = listener;
+		send(0);
+	}
+
+	/*
+	 * Receive a response.  If the resolution hasn't been completed,
+	 * either wake up the blocking thread or call the callback.
+	 */
+	public void
+	receiveMessage(Object id, Message m) {
+		if (Options.check("verbose"))
+			System.err.println("ExtendedResolver: " +
+					   "received message");
+		synchronized (this) {
+			if (done)
+				return;
+			response = m;
+			done = true;
+			if (listener == null) {
+				notifyAll();
+				return;
+			}
+		}
+		listener.receiveMessage(this, response);
+	}
+
+	/*
+	 * Receive an exception.  If the resolution has been completed,
+	 * do nothing.  Otherwise make progress.
+	 */
+	public void
+	handleException(Object id, Exception e) {
+		if (Options.check("verbose"))
+			System.err.println("ExtendedResolver: got " + e);
+		synchronized (this) {
+			outstanding--;
+			if (done)
+				return;
+			int n;
+			for (n = 0; n < inprogress.length; n++)
+				if (inprogress[n] == id)
+					break;
+			/* If we don't know what this is, do nothing. */
+			if (n == inprogress.length)
+				return;
+			boolean startnext = false;
+			/*
+			 * If this is the first response from server n, 
+			 * we should start sending queries to server n + 1.
+			 */
+			if (sent[n] == 1 && n < resolvers.length - 1)
+				startnext = true;
+			if (e instanceof InterruptedIOException) {
+				/* Got a timeout; resend */
+				if (sent[n] < retries)
+					send(n);
+				if (thrown == null)
+					thrown = e;
+			} else if (e instanceof SocketException) {
+				/*
+				 * Problem with the socket; don't resend
+				 * on it
+				 */
+				if (thrown == null ||
+				    thrown instanceof InterruptedIOException)
+					thrown = e;
+			} else {
+				/*
+				 * Problem with the response; don't resend
+				 * on the same socket.
+				 */
+				thrown = e;
+			}
+			if (done)
+				return;
+			if (startnext)
+				send(n + 1);
+			if (done)
+				return;
+			if (outstanding == 0) {
+				/*
+				 * If we're done and this is synchronous,
+				 * wake up the blocking thread.
+				 */
+				done = true;
+				if (listener == null) {
+					notifyAll();
+					return;
+				}
+			}
+			if (!done)
+				return;
+		}
+		/* If we're done and this is asynchronous, call the callback. */
+		if (!(thrown instanceof Exception))
+			thrown = new RuntimeException(thrown.getMessage());
+		listener.handleException(this, (Exception) thrown);
+	}
+}
+
+private static final int quantum = 5;
+
+private List resolvers;
+private boolean loadBalance = false;
+private int lbStart = 0;
+private int retries = 3;
+
+private void
+init() {
+	resolvers = new ArrayList();
+}
+
+/**
+ * Creates a new Extended Resolver.  The default ResolverConfig is used to
+ * determine the servers for which SimpleResolver contexts should be
+ * initialized.
+ * @see SimpleResolver
+ * @see ResolverConfig
+ * @exception UnknownHostException Failure occured initializing SimpleResolvers
+ */
+public
+ExtendedResolver() throws UnknownHostException {
+	init();
+	String [] servers = ResolverConfig.getCurrentConfig().servers();
+	if (servers != null) {
+		for (int i = 0; i < servers.length; i++) {
+			Resolver r = new SimpleResolver(servers[i]);
+			r.setTimeout(quantum);
+			resolvers.add(r);
+		}
+	}
+	else
+		resolvers.add(new SimpleResolver());
+}
+
+/**
+ * Creates a new Extended Resolver
+ * @param servers An array of server names for which SimpleResolver
+ * contexts should be initialized.
+ * @see SimpleResolver
+ * @exception UnknownHostException Failure occured initializing SimpleResolvers
+ */
+public
+ExtendedResolver(String [] servers) throws UnknownHostException {
+	init();
+	for (int i = 0; i < servers.length; i++) {
+		Resolver r = new SimpleResolver(servers[i]);
+		r.setTimeout(quantum);
+		resolvers.add(r);
+	}
+}
+
+/**
+ * Creates a new Extended Resolver
+ * @param res An array of pre-initialized Resolvers is provided.
+ * @see SimpleResolver
+ * @exception UnknownHostException Failure occured initializing SimpleResolvers
+ */
+public
+ExtendedResolver(Resolver [] res) throws UnknownHostException {
+	init();
+	for (int i = 0; i < res.length; i++)
+		resolvers.add(res[i]);
+}
+
+public void
+setPort(int port) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setPort(port);
+}
+
+public void
+setTCP(boolean flag) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setTCP(flag);
+}
+
+public void
+setIgnoreTruncation(boolean flag) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setIgnoreTruncation(flag);
+}
+
+public void
+setEDNS(int level) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setEDNS(level);
+}
+
+public void
+setEDNS(int level, int payloadSize, int flags, List options) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setEDNS(level, payloadSize,
+						     flags, options);
+}
+
+public void
+setTSIGKey(TSIG key) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setTSIGKey(key);
+}
+
+public void
+setTimeout(int secs, int msecs) {
+	for (int i = 0; i < resolvers.size(); i++)
+		((Resolver)resolvers.get(i)).setTimeout(secs, msecs);
+}
+
+public void
+setTimeout(int secs) {
+	setTimeout(secs, 0);
+}
+
+/**
+ * Sends a message and waits for a response.  Multiple servers are queried,
+ * and queries are sent multiple times until either a successful response
+ * is received, or it is clear that there is no successful response.
+ * @param query The query to send.
+ * @return The response.
+ * @throws IOException An error occurred while sending or receiving.
+ */
+public Message
+send(Message query) throws IOException {
+	Resolution res = new Resolution(this, query);
+	return res.start();
+}
+
+/**
+ * Asynchronously sends a message to multiple servers, potentially multiple
+ * times, registering a listener to receive a callback on success or exception.
+ * Multiple asynchronous lookups can be performed in parallel.  Since the
+ * callback may be invoked before the function returns, external
+ * synchronization is necessary.
+ * @param query The query to send
+ * @param listener The object containing the callbacks.
+ * @return An identifier, which is also a parameter in the callback
+ */
+public Object
+sendAsync(final Message query, final ResolverListener listener) {
+	Resolution res = new Resolution(this, query);
+	res.startAsync(listener);
+	return res;
+}
+
+/** Returns the nth resolver used by this ExtendedResolver */
+public Resolver
+getResolver(int n) {
+	if (n < resolvers.size())
+		return (Resolver)resolvers.get(n);
+	return null;
+}
+
+/** Returns all resolvers used by this ExtendedResolver */
+public Resolver []
+getResolvers() {
+	return (Resolver []) resolvers.toArray(new Resolver[resolvers.size()]);
+}
+
+/** Adds a new resolver to be used by this ExtendedResolver */
+public void
+addResolver(Resolver r) {
+	resolvers.add(r);
+}
+
+/** Deletes a resolver used by this ExtendedResolver */
+public void
+deleteResolver(Resolver r) {
+	resolvers.remove(r);
+}
+
+/** Sets whether the servers should be load balanced.
+ * @param flag If true, servers will be tried in round-robin order.  If false,
+ * servers will always be queried in the same order.
+ */
+public void
+setLoadBalance(boolean flag) {
+	loadBalance = flag;
+}
+
+/** Sets the number of retries sent to each server per query */
+public void
+setRetries(int retries) {
+	this.retries = retries;
+}
+
+}
diff --git a/src/org/xbill/DNS/Flags.java b/src/org/xbill/DNS/Flags.java
new file mode 100644
index 0000000..964ce23
--- /dev/null
+++ b/src/org/xbill/DNS/Flags.java
@@ -0,0 +1,81 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to flags in the DNS header.
+ *
+ * @author Brian Wellington
+ */
+
+public final class Flags {
+
+private static Mnemonic flags = new Mnemonic("DNS Header Flag",
+					     Mnemonic.CASE_LOWER);
+
+/** query/response */
+public static final byte QR		= 0;
+
+/** authoritative answer */
+public static final byte AA		= 5;
+
+/** truncated */
+public static final byte TC		= 6;
+
+/** recursion desired */
+public static final byte RD		= 7;
+
+/** recursion available */
+public static final byte RA		= 8;
+
+/** authenticated data */
+public static final byte AD		= 10;
+
+/** (security) checking disabled */
+public static final byte CD		= 11;
+
+/** dnssec ok (extended) */
+public static final int DO		= ExtendedFlags.DO;
+
+static {
+	flags.setMaximum(0xF);
+	flags.setPrefix("FLAG");
+	flags.setNumericAllowed(true);
+
+	flags.add(QR, "qr");
+	flags.add(AA, "aa");
+	flags.add(TC, "tc");
+	flags.add(RD, "rd");
+	flags.add(RA, "ra");
+	flags.add(AD, "ad");
+	flags.add(CD, "cd");
+}
+
+private
+Flags() {}
+
+/** Converts a numeric Flag into a String */
+public static String
+string(int i) {
+	return flags.getText(i);
+}
+
+/** Converts a String representation of an Flag into its numeric value */
+public static int
+value(String s) {
+	return flags.getValue(s);
+}
+
+/**
+ * Indicates if a bit in the flags field is a flag or not.  If it's part of
+ * the rcode or opcode, it's not.
+ */
+public static boolean
+isFlag(int index) {
+	flags.check(index);
+	if ((index >= 1 && index <= 4) || (index >= 12))
+		return false;
+	return true;
+}
+
+}
diff --git a/src/org/xbill/DNS/FormattedTime.java b/src/org/xbill/DNS/FormattedTime.java
new file mode 100644
index 0000000..c76a846
--- /dev/null
+++ b/src/org/xbill/DNS/FormattedTime.java
@@ -0,0 +1,79 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Routines for converting time values to and from YYYYMMDDHHMMSS format.
+ *
+ * @author Brian Wellington
+ */
+
+import java.util.*;
+import java.text.*;
+
+final class FormattedTime {
+
+private static NumberFormat w2, w4;
+
+static {
+	w2 = new DecimalFormat();
+	w2.setMinimumIntegerDigits(2);
+
+	w4 = new DecimalFormat();
+	w4.setMinimumIntegerDigits(4);
+	w4.setGroupingUsed(false);
+}
+
+private
+FormattedTime() {}
+
+/**
+ * Converts a Date into a formatted string.
+ * @param date The Date to convert.
+ * @return The formatted string.
+ */
+public static String
+format(Date date) {
+	Calendar c = new GregorianCalendar(TimeZone.getTimeZone("UTC"));
+	StringBuffer sb = new StringBuffer();
+
+	c.setTime(date);
+	sb.append(w4.format(c.get(Calendar.YEAR)));
+	sb.append(w2.format(c.get(Calendar.MONTH)+1));
+	sb.append(w2.format(c.get(Calendar.DAY_OF_MONTH)));
+	sb.append(w2.format(c.get(Calendar.HOUR_OF_DAY)));
+	sb.append(w2.format(c.get(Calendar.MINUTE)));
+	sb.append(w2.format(c.get(Calendar.SECOND)));
+	return sb.toString();
+}
+
+/**
+ * Parses a formatted time string into a Date.
+ * @param s The string, in the form YYYYMMDDHHMMSS.
+ * @return The Date object.
+ * @throws TextParseExcetption The string was invalid.
+ */
+public static Date
+parse(String s) throws TextParseException {
+	if (s.length() != 14) {
+		throw new TextParseException("Invalid time encoding: " + s);
+	}
+
+	Calendar c = new GregorianCalendar(TimeZone.getTimeZone("UTC"));
+	c.clear();
+	try {
+		int year = Integer.parseInt(s.substring(0, 4));
+		int month = Integer.parseInt(s.substring(4, 6)) - 1;
+		int date = Integer.parseInt(s.substring(6, 8));
+		int hour = Integer.parseInt(s.substring(8, 10));
+		int minute = Integer.parseInt(s.substring(10, 12));
+		int second = Integer.parseInt(s.substring(12, 14));
+		c.set(year, month, date, hour, minute, second);
+	}
+	catch (NumberFormatException e) {
+		throw new TextParseException("Invalid time encoding: " + s);
+	}
+	return c.getTime();
+}
+
+}
diff --git a/src/org/xbill/DNS/GPOSRecord.java b/src/org/xbill/DNS/GPOSRecord.java
new file mode 100644
index 0000000..688d567
--- /dev/null
+++ b/src/org/xbill/DNS/GPOSRecord.java
@@ -0,0 +1,178 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Geographical Location - describes the physical location of a host.
+ *
+ * @author Brian Wellington
+ */
+
+public class GPOSRecord extends Record {
+
+private static final long serialVersionUID = -6349714958085750705L;
+
+private byte [] latitude, longitude, altitude;
+
+GPOSRecord() {}
+
+Record
+getObject() {
+	return new GPOSRecord();
+}
+
+private void
+validate(double longitude, double latitude) throws IllegalArgumentException
+{
+       if (longitude < -90.0 || longitude > 90.0) {
+               throw new IllegalArgumentException("illegal longitude " +
+                                                  longitude);
+       }
+       if (latitude < -180.0 || latitude > 180.0) {
+               throw new IllegalArgumentException("illegal latitude " +
+                                                  latitude);
+       }
+}
+
+/**
+ * Creates an GPOS Record from the given data
+ * @param longitude The longitude component of the location.
+ * @param latitude The latitude component of the location.
+ * @param altitude The altitude component of the location (in meters above sea
+ * level).
+*/
+public
+GPOSRecord(Name name, int dclass, long ttl, double longitude, double latitude,
+	   double altitude)
+{
+	super(name, Type.GPOS, dclass, ttl);
+	validate(longitude, latitude);
+	this.longitude = Double.toString(longitude).getBytes();
+	this.latitude = Double.toString(latitude).getBytes();
+	this.altitude = Double.toString(altitude).getBytes();
+}
+
+/**
+ * Creates an GPOS Record from the given data
+ * @param longitude The longitude component of the location.
+ * @param latitude The latitude component of the location.
+ * @param altitude The altitude component of the location (in meters above sea
+ * level).
+*/
+public
+GPOSRecord(Name name, int dclass, long ttl, String longitude, String latitude,
+	   String altitude)
+{
+	super(name, Type.GPOS, dclass, ttl);
+	try {
+		this.longitude = byteArrayFromString(longitude);
+		this.latitude = byteArrayFromString(latitude);
+		validate(getLongitude(), getLatitude());
+		this.altitude = byteArrayFromString(altitude);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException(e.getMessage());
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	longitude = in.readCountedString();
+	latitude = in.readCountedString();
+	altitude = in.readCountedString();
+	try {
+		validate(getLongitude(), getLatitude());
+	}
+	catch(IllegalArgumentException e) {
+		throw new WireParseException(e.getMessage());
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	try {
+		longitude = byteArrayFromString(st.getString());
+		latitude = byteArrayFromString(st.getString());
+		altitude = byteArrayFromString(st.getString());
+	}
+	catch (TextParseException e) {
+		throw st.exception(e.getMessage());
+	}
+	try {
+		validate(getLongitude(), getLatitude());
+	}
+	catch(IllegalArgumentException e) {
+		throw new WireParseException(e.getMessage());
+	}
+}
+
+/** Convert to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(byteArrayToString(longitude, true));
+	sb.append(" ");
+	sb.append(byteArrayToString(latitude, true));
+	sb.append(" ");
+	sb.append(byteArrayToString(altitude, true));
+	return sb.toString();
+}
+
+/** Returns the longitude as a string */
+public String
+getLongitudeString() {
+	return byteArrayToString(longitude, false);
+}
+
+/**
+ * Returns the longitude as a double
+ * @throws NumberFormatException The string does not contain a valid numeric
+ * value.
+ */
+public double
+getLongitude() {
+	return Double.parseDouble(getLongitudeString());
+}
+
+/** Returns the latitude as a string */
+public String
+getLatitudeString() {
+	return byteArrayToString(latitude, false);
+}
+
+/**
+ * Returns the latitude as a double
+ * @throws NumberFormatException The string does not contain a valid numeric
+ * value.
+ */
+public double
+getLatitude() {
+	return Double.parseDouble(getLatitudeString());
+}
+
+/** Returns the altitude as a string */
+public String
+getAltitudeString() {
+	return byteArrayToString(altitude, false);
+}
+
+/**
+ * Returns the altitude as a double
+ * @throws NumberFormatException The string does not contain a valid numeric
+ * value.
+ */
+public double
+getAltitude() {
+	return Double.parseDouble(getAltitudeString());
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeCountedString(longitude);
+	out.writeCountedString(latitude);
+	out.writeCountedString(altitude);
+}
+
+}
diff --git a/src/org/xbill/DNS/Generator.java b/src/org/xbill/DNS/Generator.java
new file mode 100644
index 0000000..a08d343
--- /dev/null
+++ b/src/org/xbill/DNS/Generator.java
@@ -0,0 +1,264 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A representation of a $GENERATE statement in a master file.
+ *
+ * @author Brian Wellington
+ */
+
+public class Generator {
+
+/** The start of the range. */
+public long start;
+
+/** The end of the range. */
+public long end;
+
+/** The step value of the range. */
+public long step;
+
+/** The pattern to use for generating record names. */
+public final String namePattern;
+
+/** The type of the generated records. */
+public final int type;
+
+/** The class of the generated records. */
+public final int dclass;
+
+/** The ttl of the generated records. */
+public final long ttl;
+
+/** The pattern to use for generating record data. */
+public final String rdataPattern;
+
+/** The origin to append to relative names. */
+public final Name origin;
+
+private long current;
+
+/**
+ * Indicates whether generation is supported for this type.
+ * @throws InvalidTypeException The type is out of range.
+ */
+public static boolean
+supportedType(int type) {
+	Type.check(type);
+	return (type == Type.PTR || type == Type.CNAME || type == Type.DNAME ||
+		type == Type.A || type == Type.AAAA || type == Type.NS);
+}
+
+/**
+ * Creates a specification for generating records, as a $GENERATE
+ * statement in a master file.
+ * @param start The start of the range.
+ * @param end The end of the range.
+ * @param step The step value of the range.
+ * @param namePattern The pattern to use for generating record names.
+ * @param type The type of the generated records.  The supported types are
+ * PTR, CNAME, DNAME, A, AAAA, and NS.
+ * @param dclass The class of the generated records.
+ * @param ttl The ttl of the generated records.
+ * @param rdataPattern The pattern to use for generating record data.
+ * @param origin The origin to append to relative names.
+ * @throws IllegalArgumentException The range is invalid.
+ * @throws IllegalArgumentException The type does not support generation.
+ * @throws IllegalArgumentException The dclass is not a valid class.
+ */
+public
+Generator(long start, long end, long step, String namePattern,
+	  int type, int dclass, long ttl, String rdataPattern, Name origin)
+{
+	if (start < 0 || end < 0 || start > end || step <= 0)
+		throw new IllegalArgumentException
+				("invalid range specification");
+	if (!supportedType(type))
+		throw new IllegalArgumentException("unsupported type");
+	DClass.check(dclass);
+
+	this.start = start;
+	this.end = end;
+	this.step = step;
+	this.namePattern = namePattern;
+	this.type = type;
+	this.dclass = dclass;
+	this.ttl = ttl;
+	this.rdataPattern = rdataPattern;
+	this.origin = origin;
+	this.current = start;
+}
+
+private String
+substitute(String spec, long n) throws IOException {
+	boolean escaped = false;
+	byte [] str = spec.getBytes();
+	StringBuffer sb = new StringBuffer();
+
+	for (int i = 0; i < str.length; i++) {
+		char c = (char)(str[i] & 0xFF);
+		if (escaped) {
+			sb.append(c);
+			escaped = false;
+		} else if (c == '\\') {
+			if (i + 1 == str.length)
+				throw new TextParseException
+						("invalid escape character");
+			escaped = true;
+		} else if (c == '$') {
+			boolean negative = false;
+			long offset = 0;
+			long width = 0;
+			long base = 10;
+			boolean wantUpperCase = false;
+			if (i + 1 < str.length && str[i + 1] == '$') {
+				// '$$' == literal '$' for backwards
+				// compatibility with old versions of BIND.
+				c = (char)(str[++i] & 0xFF);
+				sb.append(c);
+				continue;
+			} else if (i + 1 < str.length && str[i + 1] == '{') {
+				// It's a substitution with modifiers.
+				i++;
+				if (i + 1 < str.length && str[i + 1] == '-') {
+					negative = true;
+					i++;
+				}
+				while (i + 1 < str.length) {
+					c = (char)(str[++i] & 0xFF);
+					if (c == ',' || c == '}')
+						break;
+					if (c < '0' || c > '9')
+						throw new TextParseException(
+							"invalid offset");
+					c -= '0';
+					offset *= 10;
+					offset += c;
+				}
+				if (negative)
+					offset = -offset;
+
+				if (c == ',') {
+					while (i + 1 < str.length) {
+						c = (char)(str[++i] & 0xFF);
+						if (c == ',' || c == '}')
+							break;
+						if (c < '0' || c > '9')
+							throw new
+							   TextParseException(
+							   "invalid width");
+						c -= '0';
+						width *= 10;
+						width += c;
+					}
+				}
+
+				if (c == ',') {
+					if  (i + 1 == str.length)
+						throw new TextParseException(
+							   "invalid base");
+					c = (char)(str[++i] & 0xFF);
+					if (c == 'o')
+						base = 8;
+					else if (c == 'x')
+						base = 16;
+					else if (c == 'X') {
+						base = 16;
+						wantUpperCase = true;
+					}
+					else if (c != 'd')
+						throw new TextParseException(
+							   "invalid base");
+				}
+
+				if (i + 1 == str.length || str[i + 1] != '}')
+					throw new TextParseException
+						("invalid modifiers");
+				i++;
+			}
+			long v = n + offset;
+			if (v < 0)
+				throw new TextParseException
+						("invalid offset expansion");
+			String number;
+			if (base == 8)
+				number = Long.toOctalString(v);
+			else if (base == 16)
+				number = Long.toHexString(v);
+			else
+				number = Long.toString(v);
+			if (wantUpperCase)
+				number = number.toUpperCase();
+			if (width != 0 && width > number.length()) {
+				int zeros = (int)width - number.length();
+				while (zeros-- > 0)
+					sb.append('0');
+			}
+			sb.append(number);
+		} else {
+			sb.append(c);
+		}
+	}
+	return sb.toString();
+}
+
+/**
+ * Constructs and returns the next record in the expansion.
+ * @throws IOException The name or rdata was invalid after substitutions were
+ * performed.
+ */
+public Record
+nextRecord() throws IOException {
+	if (current > end)
+		return null;
+	String namestr = substitute(namePattern, current);
+	Name name = Name.fromString(namestr, origin);
+	String rdata = substitute(rdataPattern, current);
+	current += step;
+	return Record.fromString(name, type, dclass, ttl, rdata, origin);
+}
+
+/**
+ * Constructs and returns all records in the expansion.
+ * @throws IOException The name or rdata of a record was invalid after
+ * substitutions were performed.
+ */
+public Record []
+expand() throws IOException {
+	List list = new ArrayList();
+	for (long i = start; i < end; i += step) {
+		String namestr = substitute(namePattern, current);
+		Name name = Name.fromString(namestr, origin);
+		String rdata = substitute(rdataPattern, current);
+		list.add(Record.fromString(name, type, dclass, ttl,
+					   rdata, origin));
+	}
+	return (Record []) list.toArray(new Record[list.size()]);
+}
+
+/**
+ * Converts the generate specification to a string containing the corresponding
+ * $GENERATE statement.
+ */
+public String
+toString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append("$GENERATE ");
+	sb.append(start + "-" + end);
+	if (step > 1)
+		sb.append("/" + step);
+	sb.append(" ");
+	sb.append(namePattern + " ");
+	sb.append(ttl + " ");
+	if (dclass != DClass.IN || !Options.check("noPrintIN"))
+		sb.append(DClass.string(dclass) + " ");
+	sb.append(Type.string(type) + " ");
+	sb.append(rdataPattern + " ");
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/GenericEDNSOption.java b/src/org/xbill/DNS/GenericEDNSOption.java
new file mode 100644
index 0000000..7c8b51b
--- /dev/null
+++ b/src/org/xbill/DNS/GenericEDNSOption.java
@@ -0,0 +1,47 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+package org.xbill.DNS;
+
+import java.io.*;
+
+import org.xbill.DNS.utils.base16;
+
+/**
+ * An EDNSOption with no internal structure.
+ * 
+ * @author Ming Zhou &lt;mizhou@bnivideo.com&gt;, Beaumaris Networks
+ * @author Brian Wellington
+ */
+public class GenericEDNSOption extends EDNSOption {
+
+private byte [] data;
+
+GenericEDNSOption(int code) {
+	super(code);
+}
+
+/**
+ * Construct a generic EDNS option.
+ * @param data The contents of the option.
+ */
+public 
+GenericEDNSOption(int code, byte [] data) {
+	super(code);
+	this.data = Record.checkByteArrayLength("option data", data, 0xFFFF);
+}
+
+void 
+optionFromWire(DNSInput in) throws IOException {
+	data = in.readByteArray();
+}
+
+void 
+optionToWire(DNSOutput out) {
+	out.writeByteArray(data);
+}
+
+String 
+optionToString() {
+	return "<" + base16.toString(data) + ">";
+}
+
+}
diff --git a/src/org/xbill/DNS/HINFORecord.java b/src/org/xbill/DNS/HINFORecord.java
new file mode 100644
index 0000000..18fed32
--- /dev/null
+++ b/src/org/xbill/DNS/HINFORecord.java
@@ -0,0 +1,95 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Host Information - describes the CPU and OS of a host
+ *
+ * @author Brian Wellington
+ */
+
+public class HINFORecord extends Record {
+
+private static final long serialVersionUID = -4732870630947452112L;
+	
+private byte [] cpu, os;
+
+HINFORecord() {}
+
+Record
+getObject() {
+	return new HINFORecord();
+}
+
+/**
+ * Creates an HINFO Record from the given data
+ * @param cpu A string describing the host's CPU
+ * @param os A string describing the host's OS
+ * @throws IllegalArgumentException One of the strings has invalid escapes
+ */
+public
+HINFORecord(Name name, int dclass, long ttl, String cpu, String os) {
+	super(name, Type.HINFO, dclass, ttl);
+	try {
+		this.cpu = byteArrayFromString(cpu);
+		this.os = byteArrayFromString(os);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException(e.getMessage());
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	cpu = in.readCountedString();
+	os = in.readCountedString();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	try {
+		cpu = byteArrayFromString(st.getString());
+		os = byteArrayFromString(st.getString());
+	}
+	catch (TextParseException e) {
+		throw st.exception(e.getMessage());
+	}
+}
+
+/**
+ * Returns the host's CPU
+ */
+public String
+getCPU() {
+	return byteArrayToString(cpu, false);
+}
+
+/**
+ * Returns the host's OS
+ */
+public String
+getOS() {
+	return byteArrayToString(os, false);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeCountedString(cpu);
+	out.writeCountedString(os);
+}
+
+/**
+ * Converts to a string
+ */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(byteArrayToString(cpu, true));
+	sb.append(" ");
+	sb.append(byteArrayToString(os, true));
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/Header.java b/src/org/xbill/DNS/Header.java
new file mode 100644
index 0000000..2a44d08
--- /dev/null
+++ b/src/org/xbill/DNS/Header.java
@@ -0,0 +1,286 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A DNS message header
+ * @see Message
+ *
+ * @author Brian Wellington
+ */
+
+public class Header implements Cloneable {
+
+private int id; 
+private int flags;
+private int [] counts;
+
+private static Random random = new Random();
+
+/** The length of a DNS Header in wire format. */
+public static final int LENGTH = 12;
+
+private void
+init() {
+	counts = new int[4];
+	flags = 0;
+	id = -1;
+}
+
+/**
+ * Create a new empty header.
+ * @param id The message id
+ */
+public
+Header(int id) {
+	init();
+	setID(id);
+}
+
+/**
+ * Create a new empty header with a random message id
+ */
+public
+Header() {
+	init();
+}
+
+/**
+ * Parses a Header from a stream containing DNS wire format.
+ */
+Header(DNSInput in) throws IOException {
+	this(in.readU16());
+	flags = in.readU16();
+	for (int i = 0; i < counts.length; i++)
+		counts[i] = in.readU16();
+}
+
+/**
+ * Creates a new Header from its DNS wire format representation
+ * @param b A byte array containing the DNS Header.
+ */
+public
+Header(byte [] b) throws IOException {
+	this(new DNSInput(b));
+}
+
+void
+toWire(DNSOutput out) {
+	out.writeU16(getID());
+	out.writeU16(flags);
+	for (int i = 0; i < counts.length; i++)
+		out.writeU16(counts[i]);
+}
+
+public byte []
+toWire() {
+	DNSOutput out = new DNSOutput();
+	toWire(out);
+	return out.toByteArray();
+}
+
+static private boolean
+validFlag(int bit) {
+	return (bit >= 0 && bit <= 0xF && Flags.isFlag(bit));
+}
+
+static private void
+checkFlag(int bit) {
+	if (!validFlag(bit))
+		throw new IllegalArgumentException("invalid flag bit " + bit);
+}
+
+/**
+ * Sets a flag to the supplied value
+ * @see Flags
+ */
+public void
+setFlag(int bit) {
+	checkFlag(bit);
+	// bits are indexed from left to right
+	flags |= (1 << (15 - bit));
+}
+
+/**
+ * Sets a flag to the supplied value
+ * @see Flags
+ */
+public void
+unsetFlag(int bit) {
+	checkFlag(bit);
+	// bits are indexed from left to right
+	flags &= ~(1 << (15 - bit));
+}
+
+/**
+ * Retrieves a flag
+ * @see Flags
+ */
+public boolean
+getFlag(int bit) {
+	checkFlag(bit);
+	// bits are indexed from left to right
+	return (flags & (1 << (15 - bit))) != 0;
+}
+
+boolean []
+getFlags() {
+	boolean [] array = new boolean[16];
+	for (int i = 0; i < array.length; i++)
+		if (validFlag(i))
+			array[i] = getFlag(i);
+	return array;
+}
+
+/**
+ * Retrieves the message ID
+ */
+public int
+getID() {
+	if (id >= 0)
+		return id;
+	synchronized (this) {
+		if (id < 0)
+			id = random.nextInt(0xffff);
+		return id;
+	}
+}
+
+/**
+ * Sets the message ID
+ */
+public void
+setID(int id) {
+	if (id < 0 || id > 0xffff)
+		throw new IllegalArgumentException("DNS message ID " + id +
+						   " is out of range");
+	this.id = id;
+}
+
+/**
+ * Sets the message's rcode
+ * @see Rcode
+ */
+public void
+setRcode(int value) {
+	if (value < 0 || value > 0xF)
+		throw new IllegalArgumentException("DNS Rcode " + value +
+						   " is out of range");
+	flags &= ~0xF;
+	flags |= value;
+}
+
+/**
+ * Retrieves the mesasge's rcode
+ * @see Rcode
+ */
+public int
+getRcode() {
+	return flags & 0xF;
+}
+
+/**
+ * Sets the message's opcode
+ * @see Opcode
+ */
+public void
+setOpcode(int value) {
+	if (value < 0 || value > 0xF)
+		throw new IllegalArgumentException("DNS Opcode " + value +
+						   "is out of range");
+	flags &= 0x87FF;
+	flags |= (value << 11);
+}
+
+/**
+ * Retrieves the mesasge's opcode
+ * @see Opcode
+ */
+public int
+getOpcode() {
+	return (flags >> 11) & 0xF;
+}
+
+void
+setCount(int field, int value) {
+	if (value < 0 || value > 0xFFFF)
+		throw new IllegalArgumentException("DNS section count " +
+						   value + " is out of range");
+	counts[field] = value;
+}
+
+void
+incCount(int field) {
+	if (counts[field] == 0xFFFF)
+		throw new IllegalStateException("DNS section count cannot " +
+						"be incremented");
+	counts[field]++;
+}
+
+void
+decCount(int field) {
+	if (counts[field] == 0)
+		throw new IllegalStateException("DNS section count cannot " +
+						"be decremented");
+	counts[field]--;
+}
+
+/**
+ * Retrieves the record count for the given section
+ * @see Section
+ */
+public int
+getCount(int field) {
+	return counts[field];
+}
+
+/** Converts the header's flags into a String */
+public String
+printFlags() {
+	StringBuffer sb = new StringBuffer();
+
+	for (int i = 0; i < 16; i++)
+		if (validFlag(i) && getFlag(i)) {
+			sb.append(Flags.string(i));
+			sb.append(" ");
+		}
+	return sb.toString();
+}
+
+String
+toStringWithRcode(int newrcode) {
+	StringBuffer sb = new StringBuffer();
+
+	sb.append(";; ->>HEADER<<- "); 
+	sb.append("opcode: " + Opcode.string(getOpcode()));
+	sb.append(", status: " + Rcode.string(newrcode));
+	sb.append(", id: " + getID());
+	sb.append("\n");
+
+	sb.append(";; flags: " + printFlags());
+	sb.append("; ");
+	for (int i = 0; i < 4; i++)
+		sb.append(Section.string(i) + ": " + getCount(i) + " ");
+	return sb.toString();
+}
+
+/** Converts the header into a String */
+public String
+toString() {
+	return toStringWithRcode(getRcode());
+}
+
+/* Creates a new Header identical to the current one */
+public Object
+clone() {
+	Header h = new Header();
+	h.id = id;
+	h.flags = flags;
+	System.arraycopy(counts, 0, h.counts, 0, counts.length);
+	return h;
+}
+
+}
diff --git a/src/org/xbill/DNS/IPSECKEYRecord.java b/src/org/xbill/DNS/IPSECKEYRecord.java
new file mode 100644
index 0000000..7eb2956
--- /dev/null
+++ b/src/org/xbill/DNS/IPSECKEYRecord.java
@@ -0,0 +1,231 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * IPsec Keying Material (RFC 4025)
+ *
+ * @author Brian Wellington
+ */
+
+public class IPSECKEYRecord extends Record {
+
+private static final long serialVersionUID = 3050449702765909687L;
+
+public static class Algorithm {
+	private Algorithm() {}
+
+	public static final int DSA = 1;
+	public static final int RSA = 2;
+}
+
+public static class Gateway {
+	private Gateway() {}
+
+	public static final int None = 0;
+	public static final int IPv4 = 1;
+	public static final int IPv6 = 2;
+	public static final int Name = 3;
+}
+
+private int precedence;
+private int gatewayType;
+private int algorithmType;
+private Object gateway;
+private byte [] key;
+
+IPSECKEYRecord() {} 
+
+Record
+getObject() {
+	return new IPSECKEYRecord();
+}
+
+/**
+ * Creates an IPSECKEY Record from the given data.
+ * @param precedence The record's precedence.
+ * @param gatewayType The record's gateway type.
+ * @param algorithmType The record's algorithm type.
+ * @param gateway The record's gateway.
+ * @param key The record's public key.
+ */
+public
+IPSECKEYRecord(Name name, int dclass, long ttl, int precedence,
+	       int gatewayType, int algorithmType, Object gateway,
+	       byte [] key)
+{
+	super(name, Type.IPSECKEY, dclass, ttl);
+	this.precedence = checkU8("precedence", precedence);
+	this.gatewayType = checkU8("gatewayType", gatewayType);
+	this.algorithmType = checkU8("algorithmType", algorithmType);
+	switch (gatewayType) {
+	case Gateway.None:
+		this.gateway = null;
+		break;
+	case Gateway.IPv4:
+		if (!(gateway instanceof InetAddress))
+			throw new IllegalArgumentException("\"gateway\" " +
+							   "must be an IPv4 " +
+							   "address");
+		this.gateway = gateway;
+		break;
+	case Gateway.IPv6:
+		if (!(gateway instanceof Inet6Address))
+			throw new IllegalArgumentException("\"gateway\" " +
+							   "must be an IPv6 " +
+							   "address");
+		this.gateway = gateway;
+		break;
+	case Gateway.Name:
+		if (!(gateway instanceof Name))
+			throw new IllegalArgumentException("\"gateway\" " +
+							   "must be a DNS " +
+							   "name");
+		this.gateway = checkName("gateway", (Name) gateway);
+		break;
+	default:
+		throw new IllegalArgumentException("\"gatewayType\" " +
+						   "must be between 0 and 3");
+	}
+
+	this.key = key;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	precedence = in.readU8();
+	gatewayType = in.readU8();
+	algorithmType = in.readU8();
+	switch (gatewayType) {
+	case Gateway.None:
+		gateway = null;
+		break;
+	case Gateway.IPv4:
+		gateway = InetAddress.getByAddress(in.readByteArray(4));
+		break;
+	case Gateway.IPv6:
+		gateway = InetAddress.getByAddress(in.readByteArray(16));
+		break;
+	case Gateway.Name:
+		gateway = new Name(in);
+		break;
+	default:
+		throw new WireParseException("invalid gateway type");
+	}
+	if (in.remaining() > 0)
+		key = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	precedence = st.getUInt8();
+	gatewayType = st.getUInt8();
+	algorithmType = st.getUInt8();
+	switch (gatewayType) {
+	case Gateway.None:
+		String s = st.getString();
+		if (!s.equals("."))
+			throw new TextParseException("invalid gateway format");
+		gateway = null;
+		break;
+	case Gateway.IPv4:
+		gateway = st.getAddress(Address.IPv4);
+		break;
+	case Gateway.IPv6:
+		gateway = st.getAddress(Address.IPv6);
+		break;
+	case Gateway.Name:
+		gateway = st.getName(origin);
+		break;
+	default:
+		throw new WireParseException("invalid gateway type");
+	}
+	key = st.getBase64(false);
+}
+
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(precedence);
+	sb.append(" ");
+	sb.append(gatewayType);
+	sb.append(" ");
+	sb.append(algorithmType);
+	sb.append(" ");
+	switch (gatewayType) {
+	case Gateway.None:
+		sb.append(".");
+		break;
+	case Gateway.IPv4:
+	case Gateway.IPv6:
+		InetAddress gatewayAddr = (InetAddress) gateway;
+		sb.append(gatewayAddr.getHostAddress());
+		break;
+	case Gateway.Name:
+		sb.append(gateway);
+		break;
+	}
+	if (key != null) {
+		sb.append(" ");
+		sb.append(base64.toString(key));
+	}
+	return sb.toString();
+}
+
+/** Returns the record's precedence. */
+public int
+getPrecedence() {
+	return precedence;
+}
+
+/** Returns the record's gateway type. */
+public int
+getGatewayType() {
+	return gatewayType;
+}
+
+/** Returns the record's algorithm type. */
+public int
+getAlgorithmType() {
+	return algorithmType;
+}
+
+/** Returns the record's gateway. */
+public Object
+getGateway() {
+	return gateway;
+}
+
+/** Returns the record's public key */
+public byte []
+getKey() {
+	return key;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(precedence);
+	out.writeU8(gatewayType);
+	out.writeU8(algorithmType);
+	switch (gatewayType) {
+	case Gateway.None:
+		break;
+	case Gateway.IPv4:
+	case Gateway.IPv6:
+		InetAddress gatewayAddr = (InetAddress) gateway;
+		out.writeByteArray(gatewayAddr.getAddress());
+		break;
+	case Gateway.Name:
+		Name gatewayName = (Name) gateway;
+		gatewayName.toWire(out, null, canonical);
+		break;
+	}
+	if (key != null)
+		out.writeByteArray(key);
+}
+
+}
diff --git a/src/org/xbill/DNS/ISDNRecord.java b/src/org/xbill/DNS/ISDNRecord.java
new file mode 100644
index 0000000..8f9b629
--- /dev/null
+++ b/src/org/xbill/DNS/ISDNRecord.java
@@ -0,0 +1,105 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * ISDN - identifies the ISDN number and subaddress associated with a name.
+ *
+ * @author Brian Wellington
+ */
+
+public class ISDNRecord extends Record {
+
+private static final long serialVersionUID = -8730801385178968798L;
+
+private byte [] address;
+private byte [] subAddress;
+
+ISDNRecord() {}
+
+Record
+getObject() {
+	return new ISDNRecord();
+}
+
+/**
+ * Creates an ISDN Record from the given data
+ * @param address The ISDN number associated with the domain.
+ * @param subAddress The subaddress, if any.
+ * @throws IllegalArgumentException One of the strings is invalid.
+ */
+public
+ISDNRecord(Name name, int dclass, long ttl, String address, String subAddress) {
+	super(name, Type.ISDN, dclass, ttl);
+	try {
+		this.address = byteArrayFromString(address);
+		if (subAddress != null)
+			this.subAddress = byteArrayFromString(subAddress);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException(e.getMessage());
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	address = in.readCountedString();
+	if (in.remaining() > 0)
+		subAddress = in.readCountedString();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	try {
+		address = byteArrayFromString(st.getString());
+		Tokenizer.Token t = st.get();
+		if (t.isString()) {
+			subAddress = byteArrayFromString(t.value);
+		} else {
+			st.unget();
+		}
+	}
+	catch (TextParseException e) {
+		throw st.exception(e.getMessage());
+	}
+}
+
+/**
+ * Returns the ISDN number associated with the domain.
+ */
+public String
+getAddress() {
+	return byteArrayToString(address, false);
+}
+
+/**
+ * Returns the ISDN subaddress, or null if there is none.
+ */
+public String
+getSubAddress() {
+	if (subAddress == null)
+		return null;
+	return byteArrayToString(subAddress, false);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeCountedString(address);
+	if (subAddress != null)
+		out.writeCountedString(subAddress);
+}
+
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(byteArrayToString(address, true));
+	if (subAddress != null) {
+		sb.append(" ");
+		sb.append(byteArrayToString(subAddress, true));
+	}
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/InvalidDClassException.java b/src/org/xbill/DNS/InvalidDClassException.java
new file mode 100644
index 0000000..6c95cd4
--- /dev/null
+++ b/src/org/xbill/DNS/InvalidDClassException.java
@@ -0,0 +1,18 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when an invalid dclass code is specified.
+ *
+ * @author Brian Wellington
+ */
+
+public class InvalidDClassException extends IllegalArgumentException {
+
+public
+InvalidDClassException(int dclass) {
+	super("Invalid DNS class: " + dclass);
+}
+
+}
diff --git a/src/org/xbill/DNS/InvalidTTLException.java b/src/org/xbill/DNS/InvalidTTLException.java
new file mode 100644
index 0000000..95776fe
--- /dev/null
+++ b/src/org/xbill/DNS/InvalidTTLException.java
@@ -0,0 +1,18 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when an invalid TTL is specified.
+ *
+ * @author Brian Wellington
+ */
+
+public class InvalidTTLException extends IllegalArgumentException {
+
+public
+InvalidTTLException(long ttl) {
+	super("Invalid DNS TTL: " + ttl);
+}
+
+}
diff --git a/src/org/xbill/DNS/InvalidTypeException.java b/src/org/xbill/DNS/InvalidTypeException.java
new file mode 100644
index 0000000..7c61276
--- /dev/null
+++ b/src/org/xbill/DNS/InvalidTypeException.java
@@ -0,0 +1,18 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when an invalid type code is specified.
+ *
+ * @author Brian Wellington
+ */
+
+public class InvalidTypeException extends IllegalArgumentException {
+
+public
+InvalidTypeException(int type) {
+	super("Invalid DNS type: " + type);
+}
+
+}
diff --git a/src/org/xbill/DNS/KEYBase.java b/src/org/xbill/DNS/KEYBase.java
new file mode 100644
index 0000000..59a2c6c
--- /dev/null
+++ b/src/org/xbill/DNS/KEYBase.java
@@ -0,0 +1,161 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.security.PublicKey;
+
+import org.xbill.DNS.utils.*;
+
+/**
+ * The base class for KEY/DNSKEY records, which have identical formats 
+ *
+ * @author Brian Wellington
+ */
+
+abstract class KEYBase extends Record {
+
+private static final long serialVersionUID = 3469321722693285454L;
+
+protected int flags, proto, alg;
+protected byte [] key;
+protected int footprint = -1;
+protected PublicKey publicKey = null;
+
+protected
+KEYBase() {}
+
+public
+KEYBase(Name name, int type, int dclass, long ttl, int flags, int proto,
+	int alg, byte [] key)
+{
+	super(name, type, dclass, ttl);
+	this.flags = checkU16("flags", flags);
+	this.proto = checkU8("proto", proto);
+	this.alg = checkU8("alg", alg);
+	this.key = key;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	flags = in.readU16();
+	proto = in.readU8();
+	alg = in.readU8();
+	if (in.remaining() > 0)
+		key = in.readByteArray();
+}
+
+/** Converts the DNSKEY/KEY Record to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(flags);
+	sb.append(" ");
+	sb.append(proto);
+	sb.append(" ");
+	sb.append(alg);
+	if (key != null) {
+		if (Options.check("multiline")) {
+			sb.append(" (\n");
+			sb.append(base64.formatString(key, 64, "\t", true));
+			sb.append(" ; key_tag = ");
+			sb.append(getFootprint());
+		} else {
+			sb.append(" ");
+			sb.append(base64.toString(key));
+		}
+	}
+	return sb.toString();
+}
+
+/**
+ * Returns the flags describing the key's properties
+ */
+public int
+getFlags() {
+	return flags;
+}
+
+/**
+ * Returns the protocol that the key was created for
+ */
+public int
+getProtocol() {
+	return proto;
+}
+
+/**
+ * Returns the key's algorithm
+ */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ * Returns the binary data representing the key
+ */
+public byte []
+getKey() {
+	return key;
+}
+
+/**
+ * Returns the key's footprint (after computing it)
+ */
+public int
+getFootprint() {
+	if (footprint >= 0)
+		return footprint;
+
+	int foot = 0;
+
+	DNSOutput out = new DNSOutput();
+	rrToWire(out, null, false);
+	byte [] rdata = out.toByteArray();
+
+	if (alg == DNSSEC.Algorithm.RSAMD5) {
+		int d1 = rdata[rdata.length - 3] & 0xFF;
+		int d2 = rdata[rdata.length - 2] & 0xFF;
+		foot = (d1 << 8) + d2;
+	}
+	else {
+		int i; 
+		for (i = 0; i < rdata.length - 1; i += 2) {
+			int d1 = rdata[i] & 0xFF;
+			int d2 = rdata[i + 1] & 0xFF;
+			foot += ((d1 << 8) + d2);
+		}
+		if (i < rdata.length) {
+			int d1 = rdata[i] & 0xFF;
+			foot += (d1 << 8);
+		}
+		foot += ((foot >> 16) & 0xFFFF);
+	}
+	footprint = (foot & 0xFFFF);
+	return footprint;
+}
+
+/**
+ * Returns a PublicKey corresponding to the data in this key.
+ * @throws DNSSEC.DNSSECException The key could not be converted.
+ */
+public PublicKey
+getPublicKey() throws DNSSEC.DNSSECException {
+	if (publicKey != null)
+		return publicKey;
+
+	publicKey = DNSSEC.toPublicKey(this);
+	return publicKey;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(flags);
+	out.writeU8(proto);
+	out.writeU8(alg);
+	if (key != null)
+		out.writeByteArray(key);
+}
+
+}
diff --git a/src/org/xbill/DNS/KEYRecord.java b/src/org/xbill/DNS/KEYRecord.java
new file mode 100644
index 0000000..3d2e01c
--- /dev/null
+++ b/src/org/xbill/DNS/KEYRecord.java
@@ -0,0 +1,352 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.security.PublicKey;
+import java.util.*;
+
+/**
+ * Key - contains a cryptographic public key.  The data can be converted
+ * to objects implementing java.security.interfaces.PublicKey
+ * @see DNSSEC
+ *
+ * @author Brian Wellington
+ */
+
+public class KEYRecord extends KEYBase {
+
+private static final long serialVersionUID = 6385613447571488906L;
+
+public static class Protocol {
+	/**
+	 * KEY protocol identifiers.
+	 */
+
+	private Protocol() {}
+
+	/** No defined protocol. */
+	public static final int NONE = 0;
+
+	/** Transaction Level Security */
+	public static final int TLS = 1;
+
+	/** Email */
+	public static final int EMAIL = 2;
+
+	/** DNSSEC */
+	public static final int DNSSEC = 3;
+
+	/** IPSEC Control */
+	public static final int IPSEC = 4;
+
+	/** Any protocol */
+	public static final int ANY = 255;
+
+	private static Mnemonic protocols = new Mnemonic("KEY protocol",
+							 Mnemonic.CASE_UPPER);
+
+	static {
+		protocols.setMaximum(0xFF);
+		protocols.setNumericAllowed(true);
+
+		protocols.add(NONE, "NONE");
+		protocols.add(TLS, "TLS");
+		protocols.add(EMAIL, "EMAIL");
+		protocols.add(DNSSEC, "DNSSEC");
+		protocols.add(IPSEC, "IPSEC");
+		protocols.add(ANY, "ANY");
+	}
+
+	/**
+	 * Converts an KEY protocol value into its textual representation
+	 */
+	public static String
+	string(int type) {
+		return protocols.getText(type);
+	}
+
+	/**
+	 * Converts a textual representation of a KEY protocol into its
+	 * numeric code.  Integers in the range 0..255 are also accepted.
+	 * @param s The textual representation of the protocol
+	 * @return The protocol code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return protocols.getValue(s);
+	}
+}
+	
+public static class Flags {
+	/**
+	 * KEY flags identifiers.
+	 */
+
+	private Flags() {}
+
+	/** KEY cannot be used for confidentiality */
+	public static final int NOCONF = 0x4000;
+
+	/** KEY cannot be used for authentication */
+	public static final int NOAUTH = 0x8000;
+
+	/** No key present */
+	public static final int NOKEY = 0xC000;
+
+	/** Bitmask of the use fields */
+	public static final int USE_MASK = 0xC000;
+
+	/** Flag 2 (unused) */
+	public static final int FLAG2 = 0x2000;
+
+	/** Flags extension */
+	public static final int EXTEND = 0x1000;
+
+	/** Flag 4 (unused) */
+	public static final int FLAG4 = 0x0800;
+
+	/** Flag 5 (unused) */
+	public static final int FLAG5 = 0x0400;
+
+	/** Key is owned by a user. */
+	public static final int USER = 0x0000;
+
+	/** Key is owned by a zone. */
+	public static final int ZONE = 0x0100;
+
+	/** Key is owned by a host. */
+	public static final int HOST = 0x0200;
+
+	/** Key owner type 3 (reserved). */
+	public static final int NTYP3 = 0x0300;
+
+	/** Key owner bitmask. */
+	public static final int OWNER_MASK = 0x0300;
+
+	/** Flag 8 (unused) */
+	public static final int FLAG8 = 0x0080;
+
+	/** Flag 9 (unused) */
+	public static final int FLAG9 = 0x0040;
+
+	/** Flag 10 (unused) */
+	public static final int FLAG10 = 0x0020;
+
+	/** Flag 11 (unused) */
+	public static final int FLAG11 = 0x0010;
+
+	/** Signatory value 0 */
+	public static final int SIG0 = 0;
+
+	/** Signatory value 1 */
+	public static final int SIG1 = 1;
+
+	/** Signatory value 2 */
+	public static final int SIG2 = 2;
+
+	/** Signatory value 3 */
+	public static final int SIG3 = 3;
+
+	/** Signatory value 4 */
+	public static final int SIG4 = 4;
+
+	/** Signatory value 5 */
+	public static final int SIG5 = 5;
+
+	/** Signatory value 6 */
+	public static final int SIG6 = 6;
+
+	/** Signatory value 7 */
+	public static final int SIG7 = 7;
+
+	/** Signatory value 8 */
+	public static final int SIG8 = 8;
+
+	/** Signatory value 9 */
+	public static final int SIG9 = 9;
+
+	/** Signatory value 10 */
+	public static final int SIG10 = 10;
+
+	/** Signatory value 11 */
+	public static final int SIG11 = 11;
+
+	/** Signatory value 12 */
+	public static final int SIG12 = 12;
+
+	/** Signatory value 13 */
+	public static final int SIG13 = 13;
+
+	/** Signatory value 14 */
+	public static final int SIG14 = 14;
+
+	/** Signatory value 15 */
+	public static final int SIG15 = 15;
+
+	private static Mnemonic flags = new Mnemonic("KEY flags",
+						      Mnemonic.CASE_UPPER);
+
+	static {
+		flags.setMaximum(0xFFFF);
+		flags.setNumericAllowed(false);
+
+		flags.add(NOCONF, "NOCONF");
+		flags.add(NOAUTH, "NOAUTH");
+		flags.add(NOKEY, "NOKEY");
+		flags.add(FLAG2, "FLAG2");
+		flags.add(EXTEND, "EXTEND");
+		flags.add(FLAG4, "FLAG4");
+		flags.add(FLAG5, "FLAG5");
+		flags.add(USER, "USER");
+		flags.add(ZONE, "ZONE");
+		flags.add(HOST, "HOST");
+		flags.add(NTYP3, "NTYP3");
+		flags.add(FLAG8, "FLAG8");
+		flags.add(FLAG9, "FLAG9");
+		flags.add(FLAG10, "FLAG10");
+		flags.add(FLAG11, "FLAG11");
+		flags.add(SIG0, "SIG0");
+		flags.add(SIG1, "SIG1");
+		flags.add(SIG2, "SIG2");
+		flags.add(SIG3, "SIG3");
+		flags.add(SIG4, "SIG4");
+		flags.add(SIG5, "SIG5");
+		flags.add(SIG6, "SIG6");
+		flags.add(SIG7, "SIG7");
+		flags.add(SIG8, "SIG8");
+		flags.add(SIG9, "SIG9");
+		flags.add(SIG10, "SIG10");
+		flags.add(SIG11, "SIG11");
+		flags.add(SIG12, "SIG12");
+		flags.add(SIG13, "SIG13");
+		flags.add(SIG14, "SIG14");
+		flags.add(SIG15, "SIG15");
+	}
+
+	/**
+	 * Converts a textual representation of KEY flags into its
+	 * numeric code.  Integers in the range 0..65535 are also accepted.
+	 * @param s The textual representation of the protocol
+	 * @return The protocol code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		int value;
+		try {
+			value = Integer.parseInt(s);
+			if (value >= 0 && value <= 0xFFFF) {
+				return value;
+			}
+			return -1;
+		} catch (NumberFormatException e) {
+		}
+		StringTokenizer st = new StringTokenizer(s, "|");
+		value = 0;
+		while (st.hasMoreTokens()) {
+			int val = flags.getValue(st.nextToken());
+			if (val < 0) {
+				return -1;
+			}
+			value |= val;
+		}
+		return value;
+	}
+}
+
+/* flags */
+/** This key cannot be used for confidentiality (encryption) */
+public static final int FLAG_NOCONF = Flags.NOCONF;
+
+/** This key cannot be used for authentication */
+public static final int FLAG_NOAUTH = Flags.NOAUTH;
+
+/** This key cannot be used for authentication or confidentiality */
+public static final int FLAG_NOKEY = Flags.NOKEY;
+
+/** A zone key */
+public static final int OWNER_ZONE = Flags.ZONE;
+
+/** A host/end entity key */
+public static final int OWNER_HOST = Flags.HOST;
+
+/** A user key */
+public static final int OWNER_USER = Flags.USER;
+
+/* protocols */
+/** Key was created for use with transaction level security */
+public static final int PROTOCOL_TLS = Protocol.TLS;
+
+/** Key was created for use with email */
+public static final int PROTOCOL_EMAIL = Protocol.EMAIL;
+
+/** Key was created for use with DNSSEC */
+public static final int PROTOCOL_DNSSEC = Protocol.DNSSEC;
+
+/** Key was created for use with IPSEC */
+public static final int PROTOCOL_IPSEC = Protocol.IPSEC;
+
+/** Key was created for use with any protocol */
+public static final int PROTOCOL_ANY = Protocol.ANY;
+
+KEYRecord() {}
+
+Record
+getObject() {
+	return new KEYRecord();
+}
+
+/**
+ * Creates a KEY Record from the given data
+ * @param flags Flags describing the key's properties
+ * @param proto The protocol that the key was created for
+ * @param alg The key's algorithm
+ * @param key Binary data representing the key
+ */
+public
+KEYRecord(Name name, int dclass, long ttl, int flags, int proto, int alg,
+	  byte [] key)
+{
+	super(name, Type.KEY, dclass, ttl, flags, proto, alg, key);
+}
+
+/**
+ * Creates a KEY Record from the given data
+ * @param flags Flags describing the key's properties
+ * @param proto The protocol that the key was created for
+ * @param alg The key's algorithm
+ * @param key The key as a PublicKey
+ * @throws DNSSEC.DNSSECException The PublicKey could not be converted into DNS
+ * format.
+ */
+public
+KEYRecord(Name name, int dclass, long ttl, int flags, int proto, int alg,
+	  PublicKey key) throws DNSSEC.DNSSECException
+{
+	super(name, Type.KEY, dclass, ttl, flags, proto, alg,
+	      DNSSEC.fromPublicKey(key, alg));
+	publicKey = key;
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String flagString = st.getIdentifier();
+	flags = Flags.value(flagString);
+	if (flags < 0)
+		throw st.exception("Invalid flags: " + flagString);
+	String protoString = st.getIdentifier();
+	proto = Protocol.value(protoString);
+	if (proto < 0)
+		throw st.exception("Invalid protocol: " + protoString);
+	String algString = st.getIdentifier();
+	alg = DNSSEC.Algorithm.value(algString);
+	if (alg < 0)
+		throw st.exception("Invalid algorithm: " + algString);
+	/* If this is a null KEY, there's no key data */
+	if ((flags & Flags.USE_MASK) == Flags.NOKEY)
+		key = null;
+	else
+		key = st.getBase64();
+}
+
+}
diff --git a/src/org/xbill/DNS/KXRecord.java b/src/org/xbill/DNS/KXRecord.java
new file mode 100644
index 0000000..481d21b
--- /dev/null
+++ b/src/org/xbill/DNS/KXRecord.java
@@ -0,0 +1,51 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Key Exchange - delegation of authority
+ *
+ * @author Brian Wellington
+ */
+
+public class KXRecord extends U16NameBase {
+
+private static final long serialVersionUID = 7448568832769757809L;
+
+KXRecord() {}
+
+Record
+getObject() {
+	return new KXRecord();
+}
+
+/**
+ * Creates a KX Record from the given data
+ * @param preference The preference of this KX.  Records with lower priority
+ * are preferred.
+ * @param target The host that authority is delegated to
+ */
+public
+KXRecord(Name name, int dclass, long ttl, int preference, Name target) {
+	super(name, Type.KX, dclass, ttl, preference, "preference",
+	      target, "target");
+}
+
+/** Returns the target of the KX record */
+public Name
+getTarget() {
+	return getNameField();
+}
+
+/** Returns the preference of this KX record */
+public int
+getPreference() {
+	return getU16Field();
+}
+
+public Name
+getAdditionalName() {
+	return getNameField();
+}
+
+}
diff --git a/src/org/xbill/DNS/LOCRecord.java b/src/org/xbill/DNS/LOCRecord.java
new file mode 100644
index 0000000..4eddc15
--- /dev/null
+++ b/src/org/xbill/DNS/LOCRecord.java
@@ -0,0 +1,314 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.text.*;
+
+/**
+ * Location - describes the physical location of hosts, networks, subnets.
+ *
+ * @author Brian Wellington
+ */
+
+public class LOCRecord extends Record {
+
+private static final long serialVersionUID = 9058224788126750409L;
+
+private static NumberFormat w2, w3;
+
+private long size, hPrecision, vPrecision;
+private long latitude, longitude, altitude;
+
+static {
+	w2 = new DecimalFormat();
+	w2.setMinimumIntegerDigits(2);
+
+	w3 = new DecimalFormat();
+	w3.setMinimumIntegerDigits(3);
+}
+
+LOCRecord() {}
+
+Record
+getObject() {
+	return new LOCRecord();
+}
+
+/**
+ * Creates an LOC Record from the given data
+ * @param latitude The latitude of the center of the sphere
+ * @param longitude The longitude of the center of the sphere
+ * @param altitude The altitude of the center of the sphere, in m
+ * @param size The diameter of a sphere enclosing the described entity, in m.
+ * @param hPrecision The horizontal precision of the data, in m.
+ * @param vPrecision The vertical precision of the data, in m.
+*/
+public
+LOCRecord(Name name, int dclass, long ttl, double latitude, double longitude,
+	  double altitude, double size, double hPrecision, double vPrecision)
+{
+	super(name, Type.LOC, dclass, ttl);
+	this.latitude = (long)(latitude * 3600 * 1000 + (1L << 31));
+	this.longitude = (long)(longitude * 3600 * 1000 + (1L << 31));
+	this.altitude = (long)((altitude + 100000) * 100);
+	this.size = (long)(size * 100);
+	this.hPrecision = (long)(hPrecision * 100);
+	this.vPrecision = (long)(vPrecision * 100);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	int version;
+
+	version = in.readU8();
+	if (version != 0)
+		throw new WireParseException("Invalid LOC version");
+
+	size = parseLOCformat(in.readU8());
+	hPrecision = parseLOCformat(in.readU8());
+	vPrecision = parseLOCformat(in.readU8());
+	latitude = in.readU32();
+	longitude = in.readU32();
+	altitude = in.readU32();
+}
+
+private double
+parseFixedPoint(String s)
+{
+	if (s.matches("^-?\\d+$"))
+		return Integer.parseInt(s);
+	else if (s.matches("^-?\\d+\\.\\d*$")) {
+		String [] parts = s.split("\\.");
+		double value = Integer.parseInt(parts[0]);
+		double fraction = Integer.parseInt(parts[1]);
+		if (value < 0)
+			fraction *= -1;
+		int digits = parts[1].length();
+		return value + (fraction / Math.pow(10, digits));
+	} else
+		throw new NumberFormatException();
+}
+
+private long
+parsePosition(Tokenizer st, String type) throws IOException {
+	boolean isLatitude = type.equals("latitude");
+	int deg = 0, min = 0;
+	double sec = 0;
+	long value;
+	String s;
+
+	deg = st.getUInt16();
+	if (deg > 180 || (deg > 90 && isLatitude))
+		throw st.exception("Invalid LOC " + type + " degrees");
+
+	s = st.getString();
+	try {
+		min = Integer.parseInt(s);
+		if (min < 0 || min > 59)
+			throw st.exception("Invalid LOC " + type + " minutes");
+		s = st.getString();
+		sec = parseFixedPoint(s);
+		if (sec < 0 || sec >= 60)
+			throw st.exception("Invalid LOC " + type + " seconds");
+		s = st.getString();
+	} catch (NumberFormatException e) {
+	}
+
+	if (s.length() != 1)
+		throw st.exception("Invalid LOC " + type);
+
+	value = (long) (1000 * (sec + 60L * (min + 60L * deg)));
+
+	char c = Character.toUpperCase(s.charAt(0));
+	if ((isLatitude && c == 'S') || (!isLatitude && c == 'W'))
+		value = -value;
+	else if ((isLatitude && c != 'N') || (!isLatitude && c != 'E'))
+		throw st.exception("Invalid LOC " + type);
+
+	value += (1L << 31);
+
+	return value;
+}
+
+private long
+parseDouble(Tokenizer st, String type, boolean required, long min, long max,
+	    long defaultValue)
+throws IOException
+{
+	Tokenizer.Token token = st.get();
+	if (token.isEOL()) {
+		if (required)
+			throw st.exception("Invalid LOC " + type);
+		st.unget();
+		return defaultValue;
+	}
+	String s = token.value;
+	if (s.length() > 1 && s.charAt(s.length() - 1) == 'm')
+		s = s.substring(0, s.length() - 1);
+	try {
+		long value = (long)(100 * parseFixedPoint(s));
+		if (value < min || value > max)
+			throw st.exception("Invalid LOC " + type);
+		return value;
+	}
+	catch (NumberFormatException e) {
+		throw st.exception("Invalid LOC " + type);
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	latitude = parsePosition(st, "latitude");
+	longitude = parsePosition(st, "longitude");
+	altitude = parseDouble(st, "altitude", true,
+			       -10000000, 4284967295L, 0) + 10000000;
+	size = parseDouble(st, "size", false, 0, 9000000000L, 100);
+	hPrecision = parseDouble(st, "horizontal precision", false,
+				 0, 9000000000L, 1000000);
+	vPrecision = parseDouble(st, "vertical precision", false,
+				 0, 9000000000L, 1000);
+}
+
+private void
+renderFixedPoint(StringBuffer sb, NumberFormat formatter, long value,
+		 long divisor)
+{
+	sb.append(value / divisor);
+	value %= divisor;
+	if (value != 0) {
+		sb.append(".");
+		sb.append(formatter.format(value));
+	}
+}
+
+private String
+positionToString(long value, char pos, char neg) {
+	StringBuffer sb = new StringBuffer();
+	char direction;
+
+	long temp = value - (1L << 31);
+	if (temp < 0) {
+		temp = -temp;
+		direction = neg;
+	} else
+		direction = pos;
+
+	sb.append(temp / (3600 * 1000)); /* degrees */
+	temp = temp % (3600 * 1000);
+	sb.append(" ");
+
+	sb.append(temp / (60 * 1000)); /* minutes */
+	temp = temp % (60 * 1000);
+	sb.append(" ");
+
+	renderFixedPoint(sb, w3, temp, 1000); /* seconds */
+	sb.append(" ");
+
+	sb.append(direction);
+
+	return sb.toString();
+}
+
+
+/** Convert to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+
+	/* Latitude */
+	sb.append(positionToString(latitude, 'N', 'S'));
+	sb.append(" ");
+
+	/* Latitude */
+	sb.append(positionToString(longitude, 'E', 'W'));
+	sb.append(" ");
+
+	/* Altitude */
+	renderFixedPoint(sb, w2, altitude - 10000000, 100);
+	sb.append("m ");
+
+	/* Size */
+	renderFixedPoint(sb, w2, size, 100);
+	sb.append("m ");
+
+	/* Horizontal precision */
+	renderFixedPoint(sb, w2, hPrecision, 100);
+	sb.append("m ");
+
+	/* Vertical precision */
+	renderFixedPoint(sb, w2, vPrecision, 100);
+	sb.append("m");
+
+	return sb.toString();
+}
+
+/** Returns the latitude */
+public double
+getLatitude() {  
+	return ((double)(latitude - (1L << 31))) / (3600 * 1000);
+}       
+
+/** Returns the longitude */
+public double
+getLongitude() {  
+	return ((double)(longitude - (1L << 31))) / (3600 * 1000);
+}       
+
+/** Returns the altitude */
+public double
+getAltitude() {  
+	return ((double)(altitude - 10000000)) / 100;
+}       
+
+/** Returns the diameter of the enclosing sphere */
+public double
+getSize() {  
+	return ((double)size) / 100;
+}       
+
+/** Returns the horizontal precision */
+public double
+getHPrecision() {  
+	return ((double)hPrecision) / 100;
+}       
+
+/** Returns the horizontal precision */
+public double
+getVPrecision() {  
+	return ((double)vPrecision) / 100;
+}       
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(0); /* version */
+	out.writeU8(toLOCformat(size));
+	out.writeU8(toLOCformat(hPrecision));
+	out.writeU8(toLOCformat(vPrecision));
+	out.writeU32(latitude);
+	out.writeU32(longitude);
+	out.writeU32(altitude);
+}
+
+private static long
+parseLOCformat(int b) throws WireParseException {
+	long out = b >> 4;
+	int exp = b & 0xF;
+	if (out > 9 || exp > 9)
+		throw new WireParseException("Invalid LOC Encoding");
+	while (exp-- > 0)
+		out *= 10;
+	return (out);
+}
+
+private int
+toLOCformat(long l) {
+	byte exp = 0;
+	while (l > 9) {
+		exp++;
+		l /= 10;
+	}
+	return (int)((l << 4) + exp);
+}
+
+}
diff --git a/src/org/xbill/DNS/Lookup.java b/src/org/xbill/DNS/Lookup.java
new file mode 100644
index 0000000..0beba59
--- /dev/null
+++ b/src/org/xbill/DNS/Lookup.java
@@ -0,0 +1,647 @@
+// Copyright (c) 2002-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+import java.io.*;
+import java.net.*;
+
+/**
+ * The Lookup object issues queries to caching DNS servers.  The input consists
+ * of a name, an optional type, and an optional class.  Caching is enabled
+ * by default and used when possible to reduce the number of DNS requests.
+ * A Resolver, which defaults to an ExtendedResolver initialized with the
+ * resolvers located by the ResolverConfig class, performs the queries.  A
+ * search path of domain suffixes is used to resolve relative names, and is
+ * also determined by the ResolverConfig class.
+ *
+ * A Lookup object may be reused, but should not be used by multiple threads.
+ *
+ * @see Cache
+ * @see Resolver
+ * @see ResolverConfig
+ *
+ * @author Brian Wellington
+ */
+
+public final class Lookup {
+
+private static Resolver defaultResolver;
+private static Name [] defaultSearchPath;
+private static Map defaultCaches;
+private static int defaultNdots;
+
+private Resolver resolver;
+private Name [] searchPath;
+private Cache cache;
+private boolean temporary_cache;
+private int credibility;
+private Name name;
+private int type;
+private int dclass;
+private boolean verbose;
+private int iterations;
+private boolean foundAlias;
+private boolean done;
+private boolean doneCurrent;
+private List aliases;
+private Record [] answers;
+private int result;
+private String error;
+private boolean nxdomain;
+private boolean badresponse;
+private String badresponse_error;
+private boolean networkerror;
+private boolean timedout;
+private boolean nametoolong;
+private boolean referral;
+
+private static final Name [] noAliases = new Name[0];
+
+/** The lookup was successful. */
+public static final int SUCCESSFUL = 0;
+
+/**
+ * The lookup failed due to a data or server error. Repeating the lookup
+ * would not be helpful.
+ */
+public static final int UNRECOVERABLE = 1;
+
+/**
+ * The lookup failed due to a network error. Repeating the lookup may be
+ * helpful.
+ */
+public static final int TRY_AGAIN = 2;
+
+/** The host does not exist. */
+public static final int HOST_NOT_FOUND = 3;
+
+/** The host exists, but has no records associated with the queried type. */
+public static final int TYPE_NOT_FOUND = 4;
+
+public static synchronized void
+refreshDefault() {
+
+	try {
+		defaultResolver = new ExtendedResolver();
+	}
+	catch (UnknownHostException e) {
+		throw new RuntimeException("Failed to initialize resolver");
+	}
+	defaultSearchPath = ResolverConfig.getCurrentConfig().searchPath();
+	defaultCaches = new HashMap();
+	defaultNdots = ResolverConfig.getCurrentConfig().ndots();
+}
+
+static {
+	refreshDefault();
+}
+
+/**
+ * Gets the Resolver that will be used as the default by future Lookups.
+ * @return The default resolver.
+ */
+public static synchronized Resolver
+getDefaultResolver() {
+	return defaultResolver;
+}
+
+/**
+ * Sets the default Resolver to be used as the default by future Lookups.
+ * @param resolver The default resolver.
+ */
+public static synchronized void
+setDefaultResolver(Resolver resolver) {
+	defaultResolver = resolver;
+}
+
+/**
+ * Gets the Cache that will be used as the default for the specified
+ * class by future Lookups.
+ * @param dclass The class whose cache is being retrieved.
+ * @return The default cache for the specified class.
+ */
+public static synchronized Cache
+getDefaultCache(int dclass) {
+	DClass.check(dclass);
+	Cache c = (Cache) defaultCaches.get(Mnemonic.toInteger(dclass));
+	if (c == null) {
+		c = new Cache(dclass);
+		defaultCaches.put(Mnemonic.toInteger(dclass), c);
+	}
+	return c;
+}
+
+/**
+ * Sets the Cache to be used as the default for the specified class by future
+ * Lookups.
+ * @param cache The default cache for the specified class.
+ * @param dclass The class whose cache is being set.
+ */
+public static synchronized void
+setDefaultCache(Cache cache, int dclass) {
+	DClass.check(dclass);
+	defaultCaches.put(Mnemonic.toInteger(dclass), cache);
+}
+
+/**
+ * Gets the search path that will be used as the default by future Lookups.
+ * @return The default search path.
+ */
+public static synchronized Name []
+getDefaultSearchPath() {
+	return defaultSearchPath;
+}
+
+/**
+ * Sets the search path to be used as the default by future Lookups.
+ * @param domains The default search path.
+ */
+public static synchronized void
+setDefaultSearchPath(Name [] domains) {
+	defaultSearchPath = domains;
+}
+
+/**
+ * Sets the search path that will be used as the default by future Lookups.
+ * @param domains The default search path.
+ * @throws TextParseException A name in the array is not a valid DNS name.
+ */
+public static synchronized void
+setDefaultSearchPath(String [] domains) throws TextParseException {
+	if (domains == null) {
+		defaultSearchPath = null;
+		return;
+	}
+	Name [] newdomains = new Name[domains.length];
+	for (int i = 0; i < domains.length; i++)
+		newdomains[i] = Name.fromString(domains[i], Name.root);
+	defaultSearchPath = newdomains;
+}
+
+private final void
+reset() {
+	iterations = 0;
+	foundAlias = false;
+	done = false;
+	doneCurrent = false;
+	aliases = null;
+	answers = null;
+	result = -1;
+	error = null;
+	nxdomain = false;
+	badresponse = false;
+	badresponse_error = null;
+	networkerror = false;
+	timedout = false;
+	nametoolong = false;
+	referral = false;
+	if (temporary_cache)
+		cache.clearCache();
+}
+
+/**
+ * Create a Lookup object that will find records of the given name, type,
+ * and class.  The lookup will use the default cache, resolver, and search
+ * path, and look for records that are reasonably credible.
+ * @param name The name of the desired records
+ * @param type The type of the desired records
+ * @param dclass The class of the desired records
+ * @throws IllegalArgumentException The type is a meta type other than ANY.
+ * @see Cache
+ * @see Resolver
+ * @see Credibility
+ * @see Name
+ * @see Type
+ * @see DClass
+ */
+public
+Lookup(Name name, int type, int dclass) {
+	Type.check(type);
+	DClass.check(dclass);
+	if (!Type.isRR(type) && type != Type.ANY)
+		throw new IllegalArgumentException("Cannot query for " +
+						   "meta-types other than ANY");
+	this.name = name;
+	this.type = type;
+	this.dclass = dclass;
+	synchronized (Lookup.class) {
+		this.resolver = getDefaultResolver();
+		this.searchPath = getDefaultSearchPath();
+		this.cache = getDefaultCache(dclass);
+	}
+	this.credibility = Credibility.NORMAL;
+	this.verbose = Options.check("verbose");
+	this.result = -1;
+}
+
+/**
+ * Create a Lookup object that will find records of the given name and type
+ * in the IN class.
+ * @param name The name of the desired records
+ * @param type The type of the desired records
+ * @throws IllegalArgumentException The type is a meta type other than ANY.
+ * @see #Lookup(Name,int,int)
+ */
+public
+Lookup(Name name, int type) {
+	this(name, type, DClass.IN);
+}
+
+/**
+ * Create a Lookup object that will find records of type A at the given name
+ * in the IN class.
+ * @param name The name of the desired records
+ * @see #Lookup(Name,int,int)
+ */
+public
+Lookup(Name name) {
+	this(name, Type.A, DClass.IN);
+}
+
+/**
+ * Create a Lookup object that will find records of the given name, type,
+ * and class.
+ * @param name The name of the desired records
+ * @param type The type of the desired records
+ * @param dclass The class of the desired records
+ * @throws TextParseException The name is not a valid DNS name
+ * @throws IllegalArgumentException The type is a meta type other than ANY.
+ * @see #Lookup(Name,int,int)
+ */
+public
+Lookup(String name, int type, int dclass) throws TextParseException {
+	this(Name.fromString(name), type, dclass);
+}
+
+/**
+ * Create a Lookup object that will find records of the given name and type
+ * in the IN class.
+ * @param name The name of the desired records
+ * @param type The type of the desired records
+ * @throws TextParseException The name is not a valid DNS name
+ * @throws IllegalArgumentException The type is a meta type other than ANY.
+ * @see #Lookup(Name,int,int)
+ */
+public
+Lookup(String name, int type) throws TextParseException {
+	this(Name.fromString(name), type, DClass.IN);
+}
+
+/**
+ * Create a Lookup object that will find records of type A at the given name
+ * in the IN class.
+ * @param name The name of the desired records
+ * @throws TextParseException The name is not a valid DNS name
+ * @see #Lookup(Name,int,int)
+ */
+public
+Lookup(String name) throws TextParseException {
+	this(Name.fromString(name), Type.A, DClass.IN);
+}
+
+/**
+ * Sets the resolver to use when performing this lookup.  This overrides the
+ * default value.
+ * @param resolver The resolver to use.
+ */
+public void
+setResolver(Resolver resolver) {
+	this.resolver = resolver;
+}
+
+/**
+ * Sets the search path to use when performing this lookup.  This overrides the
+ * default value.
+ * @param domains An array of names containing the search path.
+ */
+public void
+setSearchPath(Name [] domains) {
+	this.searchPath = domains;
+}
+
+/**
+ * Sets the search path to use when performing this lookup. This overrides the
+ * default value.
+ * @param domains An array of names containing the search path.
+ * @throws TextParseException A name in the array is not a valid DNS name.
+ */
+public void
+setSearchPath(String [] domains) throws TextParseException {
+	if (domains == null) {
+		this.searchPath = null;
+		return;
+	}
+	Name [] newdomains = new Name[domains.length];
+	for (int i = 0; i < domains.length; i++)
+		newdomains[i] = Name.fromString(domains[i], Name.root);
+	this.searchPath = newdomains;
+}
+
+/**
+ * Sets the cache to use when performing this lookup.  This overrides the
+ * default value.  If the results of this lookup should not be permanently
+ * cached, null can be provided here.
+ * @param cache The cache to use.
+ */
+public void
+setCache(Cache cache) {
+	if (cache == null) {
+		this.cache = new Cache(dclass);
+		this.temporary_cache = true;
+	} else {
+		this.cache = cache;
+		this.temporary_cache = false;
+	}
+}
+
+/**
+ * Sets ndots to use when performing this lookup, overriding the default value.
+ * Specifically, this refers to the number of "dots" which, if present in a
+ * name, indicate that a lookup for the absolute name should be attempted
+ * before appending any search path elements.
+ * @param ndots The ndots value to use, which must be greater than or equal to
+ * 0.
+ */
+public void
+setNdots(int ndots) {
+	if (ndots < 0)
+		throw new IllegalArgumentException("Illegal ndots value: " +
+						   ndots);
+	defaultNdots = ndots;
+}
+
+/**
+ * Sets the minimum credibility level that will be accepted when performing
+ * the lookup.  This defaults to Credibility.NORMAL.
+ * @param credibility The minimum credibility level.
+ */
+public void
+setCredibility(int credibility) {
+	this.credibility = credibility;
+}
+
+private void
+follow(Name name, Name oldname) {
+	foundAlias = true;
+	badresponse = false;
+	networkerror = false;
+	timedout = false;
+	nxdomain = false;
+	referral = false;
+	iterations++;
+	if (iterations >= 6 || name.equals(oldname)) {
+		result = UNRECOVERABLE;
+		error = "CNAME loop";
+		done = true;
+		return;
+	}
+	if (aliases == null)
+		aliases = new ArrayList();
+	aliases.add(oldname);
+	lookup(name);
+}
+
+private void
+processResponse(Name name, SetResponse response) {
+	if (response.isSuccessful()) {
+		RRset [] rrsets = response.answers();
+		List l = new ArrayList();
+		Iterator it;
+		int i;
+
+		for (i = 0; i < rrsets.length; i++) {
+			it = rrsets[i].rrs();
+			while (it.hasNext())
+				l.add(it.next());
+		}
+
+		result = SUCCESSFUL;
+		answers = (Record []) l.toArray(new Record[l.size()]);
+		done = true;
+	} else if (response.isNXDOMAIN()) {
+		nxdomain = true;
+		doneCurrent = true;
+		if (iterations > 0) {
+			result = HOST_NOT_FOUND;
+			done = true;
+		}
+	} else if (response.isNXRRSET()) {
+		result = TYPE_NOT_FOUND;
+		answers = null;
+		done = true;
+	} else if (response.isCNAME()) {
+		CNAMERecord cname = response.getCNAME();
+		follow(cname.getTarget(), name);
+	} else if (response.isDNAME()) {
+		DNAMERecord dname = response.getDNAME();
+		try {
+			follow(name.fromDNAME(dname), name);
+		} catch (NameTooLongException e) {
+			result = UNRECOVERABLE;
+			error = "Invalid DNAME target";
+			done = true;
+		}
+	} else if (response.isDelegation()) {
+		// We shouldn't get a referral.  Ignore it.
+		referral = true;
+	}
+}
+
+private void
+lookup(Name current) {
+	SetResponse sr = cache.lookupRecords(current, type, credibility);
+	if (verbose) {
+		System.err.println("lookup " + current + " " +
+				   Type.string(type));
+		System.err.println(sr);
+	}
+	processResponse(current, sr);
+	if (done || doneCurrent)
+		return;
+
+	Record question = Record.newRecord(current, type, dclass);
+	Message query = Message.newQuery(question);
+	Message response = null;
+	try {
+		response = resolver.send(query);
+	}
+	catch (IOException e) {
+		// A network error occurred.  Press on.
+		if (e instanceof InterruptedIOException)
+			timedout = true;
+		else
+			networkerror = true;
+		return;
+	}
+	int rcode = response.getHeader().getRcode();
+	if (rcode != Rcode.NOERROR && rcode != Rcode.NXDOMAIN) {
+		// The server we contacted is broken or otherwise unhelpful.
+		// Press on.
+		badresponse = true;
+		badresponse_error = Rcode.string(rcode);
+		return;
+	}
+
+	if (!query.getQuestion().equals(response.getQuestion())) {
+		// The answer doesn't match the question.  That's not good.
+		badresponse = true;
+		badresponse_error = "response does not match query";
+		return;
+	}
+
+	sr = cache.addMessage(response);
+	if (sr == null)
+		sr = cache.lookupRecords(current, type, credibility);
+	if (verbose) {
+		System.err.println("queried " + current + " " +
+				   Type.string(type));
+		System.err.println(sr);
+	}
+	processResponse(current, sr);
+}
+
+private void
+resolve(Name current, Name suffix) {
+	doneCurrent = false;
+	Name tname = null;
+	if (suffix == null)
+		tname = current;
+	else {
+		try {
+			tname = Name.concatenate(current, suffix);
+		}
+		catch (NameTooLongException e) {
+			nametoolong = true;
+			return;
+		}
+	}
+	lookup(tname);
+}
+
+/**
+ * Performs the lookup, using the specified Cache, Resolver, and search path.
+ * @return The answers, or null if none are found.
+ */
+public Record []
+run() {
+	if (done)
+		reset();
+	if (name.isAbsolute())
+		resolve(name, null);
+	else if (searchPath == null)
+		resolve(name, Name.root);
+	else {
+		if (name.labels() > defaultNdots)
+			resolve(name, Name.root);
+		if (done)
+			return answers;
+
+		for (int i = 0; i < searchPath.length; i++) {
+			resolve(name, searchPath[i]);
+			if (done)
+				return answers;
+			else if (foundAlias)
+				break;
+		}
+	}
+	if (!done) {
+		if (badresponse) {
+			result = TRY_AGAIN;
+			error = badresponse_error;
+			done = true;
+		} else if (timedout) {
+			result = TRY_AGAIN;
+			error = "timed out";
+			done = true;
+		} else if (networkerror) {
+			result = TRY_AGAIN;
+			error = "network error";
+			done = true;
+		} else if (nxdomain) {
+			result = HOST_NOT_FOUND;
+			done = true;
+		} else if (referral) {
+			result = UNRECOVERABLE;
+			error = "referral";
+			done = true;
+		} else if (nametoolong) {
+			result = UNRECOVERABLE;
+			error = "name too long";
+			done = true;
+		}
+	}
+	return answers;
+}
+
+private void
+checkDone() {
+	if (done && result != -1)
+		return;
+	StringBuffer sb = new StringBuffer("Lookup of " + name + " ");
+	if (dclass != DClass.IN)
+		sb.append(DClass.string(dclass) + " ");
+	sb.append(Type.string(type) + " isn't done");
+	throw new IllegalStateException(sb.toString());
+}
+
+/**
+ * Returns the answers from the lookup.
+ * @return The answers, or null if none are found.
+ * @throws IllegalStateException The lookup has not completed.
+ */
+public Record []
+getAnswers() {
+	checkDone();
+	return answers;
+}
+
+/**
+ * Returns all known aliases for this name.  Whenever a CNAME/DNAME is
+ * followed, an alias is added to this array.  The last element in this
+ * array will be the owner name for records in the answer, if there are any.
+ * @return The aliases.
+ * @throws IllegalStateException The lookup has not completed.
+ */
+public Name []
+getAliases() {
+	checkDone();
+	if (aliases == null)
+		return noAliases;
+	return (Name []) aliases.toArray(new Name[aliases.size()]);
+}
+
+/**
+ * Returns the result code of the lookup.
+ * @return The result code, which can be SUCCESSFUL, UNRECOVERABLE, TRY_AGAIN,
+ * HOST_NOT_FOUND, or TYPE_NOT_FOUND.
+ * @throws IllegalStateException The lookup has not completed.
+ */
+public int
+getResult() {
+	checkDone();
+	return result;
+}
+
+/**
+ * Returns an error string describing the result code of this lookup.
+ * @return A string, which may either directly correspond the result code
+ * or be more specific.
+ * @throws IllegalStateException The lookup has not completed.
+ */
+public String
+getErrorString() {
+	checkDone();
+	if (error != null)
+		return error;
+	switch (result) {
+		case SUCCESSFUL:	return "successful";
+		case UNRECOVERABLE:	return "unrecoverable error";
+		case TRY_AGAIN:		return "try again";
+		case HOST_NOT_FOUND:	return "host not found";
+		case TYPE_NOT_FOUND:	return "type not found";
+	}
+	throw new IllegalStateException("unknown result");
+}
+
+}
diff --git a/src/org/xbill/DNS/MBRecord.java b/src/org/xbill/DNS/MBRecord.java
new file mode 100644
index 0000000..6b65edf
--- /dev/null
+++ b/src/org/xbill/DNS/MBRecord.java
@@ -0,0 +1,42 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mailbox Record  - specifies a host containing a mailbox.
+ *
+ * @author Brian Wellington
+ */
+
+public class MBRecord extends SingleNameBase {
+
+private static final long serialVersionUID = 532349543479150419L;
+
+MBRecord() {}
+
+Record
+getObject() {
+	return new MBRecord();
+}
+
+/** 
+ * Creates a new MB Record with the given data
+ * @param mailbox The host containing the mailbox for the domain.
+ */
+public
+MBRecord(Name name, int dclass, long ttl, Name mailbox) {
+	super(name, Type.MB, dclass, ttl, mailbox, "mailbox");
+}
+
+/** Gets the mailbox for the domain */
+public Name
+getMailbox() {
+	return getSingleName();
+}
+
+public Name
+getAdditionalName() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/MDRecord.java b/src/org/xbill/DNS/MDRecord.java
new file mode 100644
index 0000000..dbf51af
--- /dev/null
+++ b/src/org/xbill/DNS/MDRecord.java
@@ -0,0 +1,43 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mail Destination Record  - specifies a mail agent which delivers mail
+ * for a domain (obsolete)
+ *
+ * @author Brian Wellington
+ */
+
+public class MDRecord extends SingleNameBase {
+
+private static final long serialVersionUID = 5268878603762942202L;
+
+MDRecord() {}
+
+Record
+getObject() {
+	return new MDRecord();
+}
+
+/** 
+ * Creates a new MD Record with the given data
+ * @param mailAgent The mail agent that delivers mail for the domain.
+ */
+public
+MDRecord(Name name, int dclass, long ttl, Name mailAgent) {
+	super(name, Type.MD, dclass, ttl, mailAgent, "mail agent");
+}
+
+/** Gets the mail agent for the domain */
+public Name
+getMailAgent() {
+	return getSingleName();
+}
+
+public Name
+getAdditionalName() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/MFRecord.java b/src/org/xbill/DNS/MFRecord.java
new file mode 100644
index 0000000..ff293d7
--- /dev/null
+++ b/src/org/xbill/DNS/MFRecord.java
@@ -0,0 +1,43 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mail Forwarder Record  - specifies a mail agent which forwards mail
+ * for a domain (obsolete)
+ *
+ * @author Brian Wellington
+ */
+
+public class MFRecord extends SingleNameBase {
+
+private static final long serialVersionUID = -6670449036843028169L;
+
+MFRecord() {}
+
+Record
+getObject() {
+	return new MFRecord();
+}
+
+/** 
+ * Creates a new MF Record with the given data
+ * @param mailAgent The mail agent that forwards mail for the domain.
+ */
+public
+MFRecord(Name name, int dclass, long ttl, Name mailAgent) {
+	super(name, Type.MF, dclass, ttl, mailAgent, "mail agent");
+}
+
+/** Gets the mail agent for the domain */
+public Name
+getMailAgent() {
+	return getSingleName();
+}
+
+public Name
+getAdditionalName() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/MGRecord.java b/src/org/xbill/DNS/MGRecord.java
new file mode 100644
index 0000000..5752f49
--- /dev/null
+++ b/src/org/xbill/DNS/MGRecord.java
@@ -0,0 +1,38 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mail Group Record  - specifies a mailbox which is a member of a mail group.
+ *
+ * @author Brian Wellington
+ */
+
+public class MGRecord extends SingleNameBase {
+
+private static final long serialVersionUID = -3980055550863644582L;
+
+MGRecord() {}
+
+Record
+getObject() {
+	return new MGRecord();
+}
+
+/** 
+ * Creates a new MG Record with the given data
+ * @param mailbox The mailbox that is a member of the group specified by the
+ * domain.
+ */
+public
+MGRecord(Name name, int dclass, long ttl, Name mailbox) {
+	super(name, Type.MG, dclass, ttl, mailbox, "mailbox");
+}
+
+/** Gets the mailbox in the mail group specified by the domain */
+public Name
+getMailbox() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/MINFORecord.java b/src/org/xbill/DNS/MINFORecord.java
new file mode 100644
index 0000000..4324cda
--- /dev/null
+++ b/src/org/xbill/DNS/MINFORecord.java
@@ -0,0 +1,90 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Mailbox information Record - lists the address responsible for a mailing
+ * list/mailbox and the address to receive error messages relating to the
+ * mailing list/mailbox.
+ *
+ * @author Brian Wellington
+ */
+
+public class MINFORecord extends Record {
+
+private static final long serialVersionUID = -3962147172340353796L;
+
+private Name responsibleAddress;
+private Name errorAddress;
+
+MINFORecord() {}
+
+Record
+getObject() {
+	return new MINFORecord();
+}
+
+/**
+ * Creates an MINFO Record from the given data
+ * @param responsibleAddress The address responsible for the
+ * mailing list/mailbox.
+ * @param errorAddress The address to receive error messages relating to the
+ * mailing list/mailbox.
+ */
+public
+MINFORecord(Name name, int dclass, long ttl,
+	    Name responsibleAddress, Name errorAddress)
+{
+	super(name, Type.MINFO, dclass, ttl);
+
+	this.responsibleAddress = checkName("responsibleAddress",
+					    responsibleAddress);
+	this.errorAddress = checkName("errorAddress", errorAddress);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	responsibleAddress = new Name(in);
+	errorAddress = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	responsibleAddress = st.getName(origin);
+	errorAddress = st.getName(origin);
+}
+
+/** Converts the MINFO Record to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(responsibleAddress);
+	sb.append(" ");
+	sb.append(errorAddress);
+	return sb.toString();
+}
+
+/** Gets the address responsible for the mailing list/mailbox. */
+public Name
+getResponsibleAddress() {
+	return responsibleAddress;
+}
+
+/**
+ * Gets the address to receive error messages relating to the mailing
+ * list/mailbox.
+ */
+public Name
+getErrorAddress() {
+	return errorAddress;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	responsibleAddress.toWire(out, null, canonical);
+	errorAddress.toWire(out, null, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/MRRecord.java b/src/org/xbill/DNS/MRRecord.java
new file mode 100644
index 0000000..a7ff4fc
--- /dev/null
+++ b/src/org/xbill/DNS/MRRecord.java
@@ -0,0 +1,38 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mailbox Rename Record  - specifies a rename of a mailbox.
+ *
+ * @author Brian Wellington
+ */
+
+public class MRRecord extends SingleNameBase {
+
+private static final long serialVersionUID = -5617939094209927533L;
+
+MRRecord() {}
+
+Record
+getObject() {
+	return new MRRecord();
+}
+
+/** 
+ * Creates a new MR Record with the given data
+ * @param newName The new name of the mailbox specified by the domain.
+ * domain.
+ */
+public
+MRRecord(Name name, int dclass, long ttl, Name newName) {
+	super(name, Type.MR, dclass, ttl, newName, "new name");
+}
+
+/** Gets the new name of the mailbox specified by the domain */
+public Name
+getNewName() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/MXRecord.java b/src/org/xbill/DNS/MXRecord.java
new file mode 100644
index 0000000..111977d
--- /dev/null
+++ b/src/org/xbill/DNS/MXRecord.java
@@ -0,0 +1,57 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Mail Exchange - specifies where mail to a domain is sent
+ *
+ * @author Brian Wellington
+ */
+
+public class MXRecord extends U16NameBase {
+
+private static final long serialVersionUID = 2914841027584208546L;
+
+MXRecord() {}
+
+Record
+getObject() {
+	return new MXRecord();
+}
+
+/**
+ * Creates an MX Record from the given data
+ * @param priority The priority of this MX.  Records with lower priority
+ * are preferred.
+ * @param target The host that mail is sent to
+ */
+public
+MXRecord(Name name, int dclass, long ttl, int priority, Name target) {
+	super(name, Type.MX, dclass, ttl, priority, "priority",
+	      target, "target");
+}
+
+/** Returns the target of the MX record */
+public Name
+getTarget() {
+	return getNameField();
+}
+
+/** Returns the priority of this MX record */
+public int
+getPriority() {
+	return getU16Field();
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(u16Field);
+	nameField.toWire(out, c, canonical);
+}
+
+public Name
+getAdditionalName() {
+	return getNameField();
+}
+
+}
diff --git a/src/org/xbill/DNS/Master.java b/src/org/xbill/DNS/Master.java
new file mode 100644
index 0000000..c795a9c
--- /dev/null
+++ b/src/org/xbill/DNS/Master.java
@@ -0,0 +1,427 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A DNS master file parser.  This incrementally parses the file, returning
+ * one record at a time.  When directives are seen, they are added to the
+ * state and used when parsing future records.
+ *
+ * @author Brian Wellington
+ */
+
+public class Master {
+
+private Name origin;
+private File file;
+private Record last = null;
+private long defaultTTL;
+private Master included = null;
+private Tokenizer st;
+private int currentType;
+private int currentDClass;
+private long currentTTL;
+private boolean needSOATTL;
+
+private Generator generator;
+private List generators;
+private boolean noExpandGenerate;
+
+Master(File file, Name origin, long initialTTL) throws IOException {
+	if (origin != null && !origin.isAbsolute()) {
+		throw new RelativeNameException(origin);
+	}
+	this.file = file;
+	st = new Tokenizer(file);
+	this.origin = origin;
+	defaultTTL = initialTTL;
+}
+
+/**
+ * Initializes the master file reader and opens the specified master file.
+ * @param filename The master file.
+ * @param origin The initial origin to append to relative names.
+ * @param ttl The initial default TTL.
+ * @throws IOException The master file could not be opened.
+ */
+public
+Master(String filename, Name origin, long ttl) throws IOException {
+	this(new File(filename), origin, ttl);
+}
+
+/**
+ * Initializes the master file reader and opens the specified master file.
+ * @param filename The master file.
+ * @param origin The initial origin to append to relative names.
+ * @throws IOException The master file could not be opened.
+ */
+public
+Master(String filename, Name origin) throws IOException {
+	this(new File(filename), origin, -1);
+}
+
+/**
+ * Initializes the master file reader and opens the specified master file.
+ * @param filename The master file.
+ * @throws IOException The master file could not be opened.
+ */
+public
+Master(String filename) throws IOException {
+	this(new File(filename), null, -1);
+}
+
+/**
+ * Initializes the master file reader.
+ * @param in The input stream containing a master file.
+ * @param origin The initial origin to append to relative names.
+ * @param ttl The initial default TTL.
+ */
+public
+Master(InputStream in, Name origin, long ttl) {
+	if (origin != null && !origin.isAbsolute()) {
+		throw new RelativeNameException(origin);
+	}
+	st = new Tokenizer(in);
+	this.origin = origin;
+	defaultTTL = ttl;
+}
+
+/**
+ * Initializes the master file reader.
+ * @param in The input stream containing a master file.
+ * @param origin The initial origin to append to relative names.
+ */
+public
+Master(InputStream in, Name origin) {
+	this(in, origin, -1);
+}
+
+/**
+ * Initializes the master file reader.
+ * @param in The input stream containing a master file.
+ */
+public
+Master(InputStream in) {
+	this(in, null, -1);
+}
+
+private Name
+parseName(String s, Name origin) throws TextParseException {
+	try {
+		return Name.fromString(s, origin);
+	}
+	catch (TextParseException e) {
+		throw st.exception(e.getMessage());
+	}
+}
+
+private void
+parseTTLClassAndType() throws IOException {
+	String s;
+	boolean seen_class = false;
+
+
+	// This is a bit messy, since any of the following are legal:
+	//   class ttl type
+	//   ttl class type
+	//   class type
+	//   ttl type
+	//   type
+	seen_class = false;
+	s = st.getString();
+	if ((currentDClass = DClass.value(s)) >= 0) {
+		s = st.getString();
+		seen_class = true;
+	}
+
+	currentTTL = -1;
+	try {
+		currentTTL = TTL.parseTTL(s);
+		s = st.getString();
+	}
+	catch (NumberFormatException e) {
+		if (defaultTTL >= 0)
+			currentTTL = defaultTTL;
+		else if (last != null)
+			currentTTL = last.getTTL();
+	}
+
+	if (!seen_class) {
+		if ((currentDClass = DClass.value(s)) >= 0) {
+			s = st.getString();
+		} else {
+			currentDClass = DClass.IN;
+		}
+	}
+
+	if ((currentType = Type.value(s)) < 0)
+		throw st.exception("Invalid type '" + s + "'");
+
+	// BIND allows a missing TTL for the initial SOA record, and uses
+	// the SOA minimum value.  If the SOA is not the first record,
+	// this is an error.
+	if (currentTTL < 0) {
+		if (currentType != Type.SOA)
+			throw st.exception("missing TTL");
+		needSOATTL = true;
+		currentTTL = 0;
+	}
+}
+
+private long
+parseUInt32(String s) {
+	if (!Character.isDigit(s.charAt(0)))
+		return -1;
+	try {
+		long l = Long.parseLong(s);
+		if (l < 0 || l > 0xFFFFFFFFL)
+			return -1;
+		return l;
+	}
+	catch (NumberFormatException e) {
+		return -1;
+	}
+}
+
+private void
+startGenerate() throws IOException {
+	String s;
+	int n;
+
+	// The first field is of the form start-end[/step]
+	// Regexes would be useful here.
+	s = st.getIdentifier();
+	n = s.indexOf("-");
+	if (n < 0)
+		throw st.exception("Invalid $GENERATE range specifier: " + s);
+	String startstr = s.substring(0, n);
+	String endstr = s.substring(n + 1);
+	String stepstr = null;
+	n = endstr.indexOf("/");
+	if (n >= 0) {
+		stepstr = endstr.substring(n + 1);
+		endstr = endstr.substring(0, n);
+	}
+	long start = parseUInt32(startstr);
+	long end = parseUInt32(endstr);
+	long step;
+	if (stepstr != null)
+		step = parseUInt32(stepstr);
+	else
+		step = 1;
+	if (start < 0 || end < 0 || start > end || step <= 0)
+		throw st.exception("Invalid $GENERATE range specifier: " + s);
+
+	// The next field is the name specification.
+	String nameSpec = st.getIdentifier();
+
+	// Then the ttl/class/type, in the same form as a normal record.
+	// Only some types are supported.
+	parseTTLClassAndType();
+	if (!Generator.supportedType(currentType))
+		throw st.exception("$GENERATE does not support " +
+				   Type.string(currentType) + " records");
+
+	// Next comes the rdata specification.
+	String rdataSpec = st.getIdentifier();
+
+	// That should be the end.  However, we don't want to move past the
+	// line yet, so put back the EOL after reading it.
+	st.getEOL();
+	st.unget();
+
+	generator = new Generator(start, end, step, nameSpec,
+				  currentType, currentDClass, currentTTL,
+				  rdataSpec, origin);
+	if (generators == null)
+		generators = new ArrayList(1);
+	generators.add(generator);
+}
+
+private void
+endGenerate() throws IOException {
+	// Read the EOL that we put back before.
+	st.getEOL();
+
+	generator = null;
+}
+
+private Record
+nextGenerated() throws IOException {
+	try {
+		return generator.nextRecord();
+	}
+	catch (Tokenizer.TokenizerException e) {
+		throw st.exception("Parsing $GENERATE: " + e.getBaseMessage());
+	}
+	catch (TextParseException e) {
+		throw st.exception("Parsing $GENERATE: " + e.getMessage());
+	}
+}
+
+/**
+ * Returns the next record in the master file.  This will process any
+ * directives before the next record.
+ * @return The next record.
+ * @throws IOException The master file could not be read, or was syntactically
+ * invalid.
+ */
+public Record
+_nextRecord() throws IOException {
+	Tokenizer.Token token;
+	String s;
+
+	if (included != null) {
+		Record rec = included.nextRecord();
+		if (rec != null)
+			return rec;
+		included = null;
+	}
+	if (generator != null) {
+		Record rec = nextGenerated();
+		if (rec != null)
+			return rec;
+		endGenerate();
+	}
+	while (true) {
+		Name name;
+
+		token = st.get(true, false);
+		if (token.type == Tokenizer.WHITESPACE) {
+			Tokenizer.Token next = st.get();
+			if (next.type == Tokenizer.EOL)
+				continue;
+			else if (next.type == Tokenizer.EOF)
+				return null;
+			else
+				st.unget();
+			if (last == null)
+				throw st.exception("no owner");
+			name = last.getName();
+		}
+		else if (token.type == Tokenizer.EOL)
+			continue;
+		else if (token.type == Tokenizer.EOF)
+			return null;
+		else if (((String) token.value).charAt(0) == '$') {
+			s = token.value;
+
+			if (s.equalsIgnoreCase("$ORIGIN")) {
+				origin = st.getName(Name.root);
+				st.getEOL();
+				continue;
+			} else if (s.equalsIgnoreCase("$TTL")) {
+				defaultTTL = st.getTTL();
+				st.getEOL();
+				continue;
+			} else  if (s.equalsIgnoreCase("$INCLUDE")) {
+				String filename = st.getString();
+				File newfile;
+				if (file != null) {
+					String parent = file.getParent();
+					newfile = new File(parent, filename);
+				} else {
+					newfile = new File(filename);
+				}
+				Name incorigin = origin;
+				token = st.get();
+				if (token.isString()) {
+					incorigin = parseName(token.value,
+							      Name.root);
+					st.getEOL();
+				}
+				included = new Master(newfile, incorigin,
+						      defaultTTL);
+				/*
+				 * If we continued, we wouldn't be looking in
+				 * the new file.  Recursing works better.
+				 */
+				return nextRecord();
+			} else  if (s.equalsIgnoreCase("$GENERATE")) {
+				if (generator != null)
+					throw new IllegalStateException
+						("cannot nest $GENERATE");
+				startGenerate();
+				if (noExpandGenerate) {
+					endGenerate();
+					continue;
+				}
+				return nextGenerated();
+			} else {
+				throw st.exception("Invalid directive: " + s);
+			}
+		} else {
+			s = token.value;
+			name = parseName(s, origin);
+			if (last != null && name.equals(last.getName())) {
+				name = last.getName();
+			}
+		}
+
+		parseTTLClassAndType();
+		last = Record.fromString(name, currentType, currentDClass,
+					 currentTTL, st, origin);
+		if (needSOATTL) {
+			long ttl = ((SOARecord)last).getMinimum();
+			last.setTTL(ttl);
+			defaultTTL = ttl;
+			needSOATTL = false;
+		}
+		return last;
+	}
+}
+
+/**
+ * Returns the next record in the master file.  This will process any
+ * directives before the next record.
+ * @return The next record.
+ * @throws IOException The master file could not be read, or was syntactically
+ * invalid.
+ */
+public Record
+nextRecord() throws IOException {
+	Record rec = null;
+	try {
+		rec = _nextRecord();
+	}
+	finally {
+		if (rec == null) {
+			st.close();
+		}
+	}
+	return rec;
+}
+
+/**
+ * Specifies whether $GENERATE statements should be expanded.  Whether
+ * expanded or not, the specifications for generated records are available
+ * by calling {@link #generators}.  This must be called before a $GENERATE
+ * statement is seen during iteration to have an effect.
+ */
+public void
+expandGenerate(boolean wantExpand) {
+	noExpandGenerate = !wantExpand;
+}
+
+/**
+ * Returns an iterator over the generators specified in the master file; that
+ * is, the parsed contents of $GENERATE statements.
+ * @see Generator
+ */
+public Iterator
+generators() {
+	if (generators != null)
+		return Collections.unmodifiableList(generators).iterator();
+	else
+		return Collections.EMPTY_LIST.iterator();
+}
+
+protected void
+finalize() {
+	st.close();
+}
+
+}
diff --git a/src/org/xbill/DNS/Message.java b/src/org/xbill/DNS/Message.java
new file mode 100644
index 0000000..fe0c3c9
--- /dev/null
+++ b/src/org/xbill/DNS/Message.java
@@ -0,0 +1,611 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+import java.io.*;
+
+/**
+ * A DNS Message.  A message is the basic unit of communication between
+ * the client and server of a DNS operation.  A message consists of a Header
+ * and 4 message sections.
+ * @see Resolver
+ * @see Header
+ * @see Section
+ *
+ * @author Brian Wellington
+ */
+
+public class Message implements Cloneable {
+
+/** The maximum length of a message in wire format. */
+public static final int MAXLENGTH = 65535;
+
+private Header header;
+private List [] sections;
+private int size;
+private TSIG tsigkey;
+private TSIGRecord querytsig;
+private int tsigerror;
+
+int tsigstart;
+int tsigState;
+int sig0start;
+
+/* The message was not signed */
+static final int TSIG_UNSIGNED = 0;
+
+/* The message was signed and verification succeeded */
+static final int TSIG_VERIFIED = 1;
+
+/* The message was an unsigned message in multiple-message response */
+static final int TSIG_INTERMEDIATE = 2;
+
+/* The message was signed and no verification was attempted.  */
+static final int TSIG_SIGNED = 3;
+
+/*
+ * The message was signed and verification failed, or was not signed
+ * when it should have been.
+ */
+static final int TSIG_FAILED = 4;
+
+private static Record [] emptyRecordArray = new Record[0];
+private static RRset [] emptyRRsetArray = new RRset[0];
+
+private
+Message(Header header) {
+	sections = new List[4];
+	this.header = header;
+}
+
+/** Creates a new Message with the specified Message ID */
+public
+Message(int id) {
+	this(new Header(id));
+}
+
+/** Creates a new Message with a random Message ID */
+public
+Message() {
+	this(new Header());
+}
+
+/**
+ * Creates a new Message with a random Message ID suitable for sending as a
+ * query.
+ * @param r A record containing the question
+ */
+public static Message
+newQuery(Record r) {
+	Message m = new Message();
+	m.header.setOpcode(Opcode.QUERY);
+	m.header.setFlag(Flags.RD);
+	m.addRecord(r, Section.QUESTION);
+	return m;
+}
+
+/**
+ * Creates a new Message to contain a dynamic update.  A random Message ID
+ * and the zone are filled in.
+ * @param zone The zone to be updated
+ */
+public static Message
+newUpdate(Name zone) {
+	return new Update(zone);
+}
+
+Message(DNSInput in) throws IOException {
+	this(new Header(in));
+	boolean isUpdate = (header.getOpcode() == Opcode.UPDATE);
+	boolean truncated = header.getFlag(Flags.TC);
+	try {
+		for (int i = 0; i < 4; i++) {
+			int count = header.getCount(i);
+			if (count > 0)
+				sections[i] = new ArrayList(count);
+			for (int j = 0; j < count; j++) {
+				int pos = in.current();
+				Record rec = Record.fromWire(in, i, isUpdate);
+				sections[i].add(rec);
+				if (i == Section.ADDITIONAL) {
+					if (rec.getType() == Type.TSIG)
+						tsigstart = pos;
+					if (rec.getType() == Type.SIG) {
+						SIGRecord sig = (SIGRecord) rec;
+						if (sig.getTypeCovered() == 0)
+							sig0start = pos;
+					}
+				}
+			}
+		}
+	} catch (WireParseException e) {
+		if (!truncated)
+			throw e;
+	}
+	size = in.current();
+}
+
+/**
+ * Creates a new Message from its DNS wire format representation
+ * @param b A byte array containing the DNS Message.
+ */
+public
+Message(byte [] b) throws IOException {
+	this(new DNSInput(b));
+}
+
+/**
+ * Replaces the Header with a new one.
+ * @see Header
+ */
+public void
+setHeader(Header h) {
+	header = h;
+}
+
+/**
+ * Retrieves the Header.
+ * @see Header
+ */
+public Header
+getHeader() {
+	return header;
+}
+
+/**
+ * Adds a record to a section of the Message, and adjusts the header.
+ * @see Record
+ * @see Section
+ */
+public void
+addRecord(Record r, int section) {
+	if (sections[section] == null)
+		sections[section] = new LinkedList();
+	header.incCount(section);
+	sections[section].add(r);
+}
+
+/**
+ * Removes a record from a section of the Message, and adjusts the header.
+ * @see Record
+ * @see Section
+ */
+public boolean
+removeRecord(Record r, int section) {
+	if (sections[section] != null && sections[section].remove(r)) {
+		header.decCount(section);
+		return true;
+	}
+	else
+		return false;
+}
+
+/**
+ * Removes all records from a section of the Message, and adjusts the header.
+ * @see Record
+ * @see Section
+ */
+public void
+removeAllRecords(int section) {
+	sections[section] = null;
+	header.setCount(section, 0);
+}
+
+/**
+ * Determines if the given record is already present in the given section.
+ * @see Record
+ * @see Section
+ */
+public boolean
+findRecord(Record r, int section) {
+	return (sections[section] != null && sections[section].contains(r));
+}
+
+/**
+ * Determines if the given record is already present in any section.
+ * @see Record
+ * @see Section
+ */
+public boolean
+findRecord(Record r) {
+	for (int i = Section.ANSWER; i <= Section.ADDITIONAL; i++)
+		if (sections[i] != null && sections[i].contains(r))
+			return true;
+	return false;
+}
+
+/**
+ * Determines if an RRset with the given name and type is already
+ * present in the given section.
+ * @see RRset
+ * @see Section
+ */
+public boolean
+findRRset(Name name, int type, int section) {
+	if (sections[section] == null)
+		return false;
+	for (int i = 0; i < sections[section].size(); i++) {
+		Record r = (Record) sections[section].get(i);
+		if (r.getType() == type && name.equals(r.getName()))
+			return true;
+	}
+	return false;
+}
+
+/**
+ * Determines if an RRset with the given name and type is already
+ * present in any section.
+ * @see RRset
+ * @see Section
+ */
+public boolean
+findRRset(Name name, int type) {
+	return (findRRset(name, type, Section.ANSWER) ||
+		findRRset(name, type, Section.AUTHORITY) ||
+		findRRset(name, type, Section.ADDITIONAL));
+}
+
+/**
+ * Returns the first record in the QUESTION section.
+ * @see Record
+ * @see Section
+ */
+public Record
+getQuestion() {
+	List l = sections[Section.QUESTION];
+	if (l == null || l.size() == 0)
+		return null;
+	return (Record) l.get(0);
+}
+
+/**
+ * Returns the TSIG record from the ADDITIONAL section, if one is present.
+ * @see TSIGRecord
+ * @see TSIG
+ * @see Section
+ */
+public TSIGRecord
+getTSIG() {
+	int count = header.getCount(Section.ADDITIONAL);
+	if (count == 0)
+		return null;
+	List l = sections[Section.ADDITIONAL];
+	Record rec = (Record) l.get(count - 1);
+	if (rec.type !=  Type.TSIG)
+		return null;
+	return (TSIGRecord) rec;
+}
+
+/**
+ * Was this message signed by a TSIG?
+ * @see TSIG
+ */
+public boolean
+isSigned() {
+	return (tsigState == TSIG_SIGNED ||
+		tsigState == TSIG_VERIFIED ||
+		tsigState == TSIG_FAILED);
+}
+
+/**
+ * If this message was signed by a TSIG, was the TSIG verified?
+ * @see TSIG
+ */
+public boolean
+isVerified() {
+	return (tsigState == TSIG_VERIFIED);
+}
+
+/**
+ * Returns the OPT record from the ADDITIONAL section, if one is present.
+ * @see OPTRecord
+ * @see Section
+ */
+public OPTRecord
+getOPT() {
+	Record [] additional = getSectionArray(Section.ADDITIONAL);
+	for (int i = 0; i < additional.length; i++)
+		if (additional[i] instanceof OPTRecord)
+			return (OPTRecord) additional[i];
+	return null;
+}
+
+/**
+ * Returns the message's rcode (error code).  This incorporates the EDNS
+ * extended rcode.
+ */
+public int
+getRcode() {
+	int rcode = header.getRcode();
+	OPTRecord opt = getOPT();
+	if (opt != null)
+		rcode += (opt.getExtendedRcode() << 4);
+	return rcode;
+}
+
+/**
+ * Returns an array containing all records in the given section, or an
+ * empty array if the section is empty.
+ * @see Record
+ * @see Section
+ */
+public Record []
+getSectionArray(int section) {
+	if (sections[section] == null)
+		return emptyRecordArray;
+	List l = sections[section];
+	return (Record []) l.toArray(new Record[l.size()]);
+}
+
+private static boolean
+sameSet(Record r1, Record r2) {
+	return (r1.getRRsetType() == r2.getRRsetType() &&
+		r1.getDClass() == r2.getDClass() &&
+		r1.getName().equals(r2.getName()));
+}
+
+/**
+ * Returns an array containing all records in the given section grouped into
+ * RRsets.
+ * @see RRset
+ * @see Section
+ */
+public RRset []
+getSectionRRsets(int section) {
+	if (sections[section] == null)
+		return emptyRRsetArray;
+	List sets = new LinkedList();
+	Record [] recs = getSectionArray(section);
+	Set hash = new HashSet();
+	for (int i = 0; i < recs.length; i++) {
+		Name name = recs[i].getName();
+		boolean newset = true;
+		if (hash.contains(name)) {
+			for (int j = sets.size() - 1; j >= 0; j--) {
+				RRset set = (RRset) sets.get(j);
+				if (set.getType() == recs[i].getRRsetType() &&
+				    set.getDClass() == recs[i].getDClass() &&
+				    set.getName().equals(name))
+				{
+					set.addRR(recs[i]);
+					newset = false;
+					break;
+				}
+			}
+		}
+		if (newset) {
+			RRset set = new RRset(recs[i]);
+			sets.add(set);
+			hash.add(name);
+		}
+	}
+	return (RRset []) sets.toArray(new RRset[sets.size()]);
+}
+
+void
+toWire(DNSOutput out) {
+	header.toWire(out);
+	Compression c = new Compression();
+	for (int i = 0; i < 4; i++) {
+		if (sections[i] == null)
+			continue;
+		for (int j = 0; j < sections[i].size(); j++) {
+			Record rec = (Record)sections[i].get(j);
+			rec.toWire(out, i, c);
+		}
+	}
+}
+
+/* Returns the number of records not successfully rendered. */
+private int
+sectionToWire(DNSOutput out, int section, Compression c,
+	      int maxLength)
+{
+	int n = sections[section].size();
+	int pos = out.current();
+	int rendered = 0;
+	Record lastrec = null;
+
+	for (int i = 0; i < n; i++) {
+		Record rec = (Record)sections[section].get(i);
+		if (lastrec != null && !sameSet(rec, lastrec)) {
+			pos = out.current();
+			rendered = i;
+		}
+		lastrec = rec;
+		rec.toWire(out, section, c);
+		if (out.current() > maxLength) {
+			out.jump(pos);
+			return n - rendered;
+		}
+	}
+	return 0;
+}
+
+/* Returns true if the message could be rendered. */
+private boolean
+toWire(DNSOutput out, int maxLength) {
+	if (maxLength < Header.LENGTH)
+		return false;
+
+	Header newheader = null;
+
+	int tempMaxLength = maxLength;
+	if (tsigkey != null)
+		tempMaxLength -= tsigkey.recordLength();
+
+	int startpos = out.current();
+	header.toWire(out);
+	Compression c = new Compression();
+	for (int i = 0; i < 4; i++) {
+		int skipped;
+		if (sections[i] == null)
+			continue;
+		skipped = sectionToWire(out, i, c, tempMaxLength);
+		if (skipped != 0) {
+			if (newheader == null)
+				newheader = (Header) header.clone();
+			if (i != Section.ADDITIONAL)
+				newheader.setFlag(Flags.TC);
+			int count = newheader.getCount(i);
+			newheader.setCount(i, count - skipped);
+			for (int j = i + 1; j < 4; j++)
+				newheader.setCount(j, 0);
+
+			out.save();
+			out.jump(startpos);
+			newheader.toWire(out);
+			out.restore();
+			break;
+		}
+	}
+
+	if (tsigkey != null) {
+		TSIGRecord tsigrec = tsigkey.generate(this, out.toByteArray(),
+						      tsigerror, querytsig);
+
+		if (newheader == null)
+			newheader = (Header) header.clone();
+		tsigrec.toWire(out, Section.ADDITIONAL, c);
+		newheader.incCount(Section.ADDITIONAL);
+
+		out.save();
+		out.jump(startpos);
+		newheader.toWire(out);
+		out.restore();
+	}
+
+	return true;
+}
+
+/**
+ * Returns an array containing the wire format representation of the Message.
+ */
+public byte []
+toWire() {
+	DNSOutput out = new DNSOutput();
+	toWire(out);
+	size = out.current();
+	return out.toByteArray();
+}
+
+/**
+ * Returns an array containing the wire format representation of the Message
+ * with the specified maximum length.  This will generate a truncated
+ * message (with the TC bit) if the message doesn't fit, and will also
+ * sign the message with the TSIG key set by a call to setTSIG().  This
+ * method may return null if the message could not be rendered at all; this
+ * could happen if maxLength is smaller than a DNS header, for example.
+ * @param maxLength The maximum length of the message.
+ * @return The wire format of the message, or null if the message could not be
+ * rendered into the specified length.
+ * @see Flags
+ * @see TSIG
+ */
+public byte []
+toWire(int maxLength) {
+	DNSOutput out = new DNSOutput();
+	toWire(out, maxLength);
+	size = out.current();
+	return out.toByteArray();
+}
+
+/**
+ * Sets the TSIG key and other necessary information to sign a message.
+ * @param key The TSIG key.
+ * @param error The value of the TSIG error field.
+ * @param querytsig If this is a response, the TSIG from the request.
+ */
+public void
+setTSIG(TSIG key, int error, TSIGRecord querytsig) {
+	this.tsigkey = key;
+	this.tsigerror = error;
+	this.querytsig = querytsig;
+}
+
+/**
+ * Returns the size of the message.  Only valid if the message has been
+ * converted to or from wire format.
+ */
+public int
+numBytes() {
+	return size;
+}
+
+/**
+ * Converts the given section of the Message to a String.
+ * @see Section
+ */
+public String
+sectionToString(int i) {
+	if (i > 3)
+		return null;
+
+	StringBuffer sb = new StringBuffer();
+
+	Record [] records = getSectionArray(i);
+	for (int j = 0; j < records.length; j++) {
+		Record rec = records[j];
+		if (i == Section.QUESTION) {
+			sb.append(";;\t" + rec.name);
+			sb.append(", type = " + Type.string(rec.type));
+			sb.append(", class = " + DClass.string(rec.dclass));
+		}
+		else
+			sb.append(rec);
+		sb.append("\n");
+	}
+	return sb.toString();
+}
+
+/**
+ * Converts the Message to a String.
+ */
+public String
+toString() {
+	StringBuffer sb = new StringBuffer();
+	OPTRecord opt = getOPT();
+	if (opt != null)
+		sb.append(header.toStringWithRcode(getRcode()) + "\n");
+	else
+		sb.append(header + "\n");
+	if (isSigned()) {
+		sb.append(";; TSIG ");
+		if (isVerified())
+			sb.append("ok");
+		else
+			sb.append("invalid");
+		sb.append('\n');
+	}
+	for (int i = 0; i < 4; i++) {
+		if (header.getOpcode() != Opcode.UPDATE)
+			sb.append(";; " + Section.longString(i) + ":\n");
+		else
+			sb.append(";; " + Section.updString(i) + ":\n");
+		sb.append(sectionToString(i) + "\n");
+	}
+	sb.append(";; Message size: " + numBytes() + " bytes");
+	return sb.toString();
+}
+
+/**
+ * Creates a copy of this Message.  This is done by the Resolver before adding
+ * TSIG and OPT records, for example.
+ * @see Resolver
+ * @see TSIGRecord
+ * @see OPTRecord
+ */
+public Object
+clone() {
+	Message m = new Message();
+	for (int i = 0; i < sections.length; i++) {
+		if (sections[i] != null)
+			m.sections[i] = new LinkedList(sections[i]);
+	}
+	m.header = (Header) header.clone();
+	m.size = size;
+	return m;
+}
+
+}
diff --git a/src/org/xbill/DNS/Mnemonic.java b/src/org/xbill/DNS/Mnemonic.java
new file mode 100644
index 0000000..dd60f62
--- /dev/null
+++ b/src/org/xbill/DNS/Mnemonic.java
@@ -0,0 +1,210 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.HashMap;
+
+/**
+ * A utility class for converting between numeric codes and mnemonics
+ * for those codes.  Mnemonics are case insensitive.
+ *
+ * @author Brian Wellington
+ */
+
+class Mnemonic {
+
+private static Integer cachedInts[] = new Integer[64];
+
+static {
+	for (int i = 0; i < cachedInts.length; i++) {
+		cachedInts[i] = new Integer(i);
+	}
+}
+
+/* Strings are case-sensitive. */
+static final int CASE_SENSITIVE = 1;
+
+/* Strings will be stored/searched for in uppercase. */
+static final int CASE_UPPER = 2;
+
+/* Strings will be stored/searched for in lowercase. */
+static final int CASE_LOWER = 3;
+
+private HashMap strings;
+private HashMap values;
+private String description;
+private int wordcase;
+private String prefix;
+private int max;
+private boolean numericok;
+
+/**
+ * Creates a new Mnemonic table.
+ * @param description A short description of the mnemonic to use when
+ * @param wordcase Whether to convert strings into uppercase, lowercase,
+ * or leave them unchanged.
+ * throwing exceptions.
+ */
+public
+Mnemonic(String description, int wordcase) {
+	this.description = description;
+	this.wordcase = wordcase;
+	strings = new HashMap();
+	values = new HashMap();
+	max = Integer.MAX_VALUE;
+}
+
+/** Sets the maximum numeric value */
+public void
+setMaximum(int max) {
+	this.max = max;
+}
+
+/**
+ * Sets the prefix to use when converting to and from values that don't
+ * have mnemonics.
+ */
+public void
+setPrefix(String prefix) {
+	this.prefix = sanitize(prefix);
+}
+
+/**
+ * Sets whether numeric values stored in strings are acceptable.
+ */
+public void
+setNumericAllowed(boolean numeric) {
+	this.numericok = numeric;
+}
+
+/**
+ * Converts an int into a possibly cached Integer.
+ */
+public static Integer
+toInteger(int val) {
+	if (val >= 0 && val < cachedInts.length)
+		return (cachedInts[val]);
+	return new Integer(val);
+}       
+
+/**
+ * Checks that a numeric value is within the range [0..max]
+ */
+public void
+check(int val) {
+	if (val < 0 || val > max) {
+		throw new IllegalArgumentException(description + " " + val +
+						   "is out of range");
+	}
+}
+
+/* Converts a String to the correct case. */
+private String
+sanitize(String str) {
+	if (wordcase == CASE_UPPER)
+		return str.toUpperCase();
+	else if (wordcase == CASE_LOWER)
+		return str.toLowerCase();
+	return str;
+}
+
+private int
+parseNumeric(String s) {
+	try {
+		int val = Integer.parseInt(s);
+		if (val >= 0 && val <= max)
+			return val;
+	}
+	catch (NumberFormatException e) {
+	}
+	return -1;
+}
+
+/**
+ * Defines the text representation of a numeric value.
+ * @param val The numeric value
+ * @param string The text string
+ */
+public void
+add(int val, String str) {
+	check(val);
+	Integer value = toInteger(val);
+	str = sanitize(str);
+	strings.put(str, value);
+	values.put(value, str);
+}
+
+/**
+ * Defines an additional text representation of a numeric value.  This will
+ * be used by getValue(), but not getText().
+ * @param val The numeric value
+ * @param string The text string
+ */
+public void
+addAlias(int val, String str) {
+	check(val);
+	Integer value = toInteger(val);
+	str = sanitize(str);
+	strings.put(str, value);
+}
+
+/**
+ * Copies all mnemonics from one table into another.
+ * @param val The numeric value
+ * @param string The text string
+ * @throws IllegalArgumentException The wordcases of the Mnemonics do not
+ * match.
+ */
+public void
+addAll(Mnemonic source) {
+	if (wordcase != source.wordcase)
+		throw new IllegalArgumentException(source.description +
+						   ": wordcases do not match");
+	strings.putAll(source.strings);
+	values.putAll(source.values);
+}
+
+/**
+ * Gets the text mnemonic corresponding to a numeric value.
+ * @param val The numeric value
+ * @return The corresponding text mnemonic.
+ */
+public String
+getText(int val) {
+	check(val);
+	String str = (String) values.get(toInteger(val));
+	if (str != null)
+		return str;
+	str = Integer.toString(val);
+	if (prefix != null)
+		return prefix + str;
+	return str;
+}
+
+/**
+ * Gets the numeric value corresponding to a text mnemonic.
+ * @param str The text mnemonic
+ * @return The corresponding numeric value, or -1 if there is none
+ */
+public int
+getValue(String str) {
+	str = sanitize(str);
+	Integer value = (Integer) strings.get(str);
+	if (value != null) {
+		return value.intValue();
+	}
+	if (prefix != null) {
+		if (str.startsWith(prefix)) {
+			int val = parseNumeric(str.substring(prefix.length()));
+			if (val >= 0) {
+				return val;
+			}
+		}
+	}
+	if (numericok) {
+		return parseNumeric(str);
+	}
+	return -1;
+}
+
+}
diff --git a/src/org/xbill/DNS/NAPTRRecord.java b/src/org/xbill/DNS/NAPTRRecord.java
new file mode 100644
index 0000000..da2ec6d
--- /dev/null
+++ b/src/org/xbill/DNS/NAPTRRecord.java
@@ -0,0 +1,154 @@
+// Copyright (c) 2000-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Name Authority Pointer Record  - specifies rewrite rule, that when applied
+ * to an existing string will produce a new domain.
+ *
+ * @author Chuck Santos
+ */
+
+public class NAPTRRecord extends Record {
+
+private static final long serialVersionUID = 5191232392044947002L;
+
+private int order, preference;
+private byte [] flags, service, regexp;
+private Name replacement;
+
+NAPTRRecord() {}
+
+Record
+getObject() {
+	return new NAPTRRecord();
+}
+
+/**
+ * Creates an NAPTR Record from the given data
+ * @param order The order of this NAPTR.  Records with lower order are
+ * preferred.
+ * @param preference The preference, used to select between records at the
+ * same order.
+ * @param flags The control aspects of the NAPTRRecord.
+ * @param service The service or protocol available down the rewrite path.
+ * @param regexp The regular/substitution expression.
+ * @param replacement The domain-name to query for the next DNS resource
+ * record, depending on the value of the flags field.
+ * @throws IllegalArgumentException One of the strings has invalid escapes
+ */
+public
+NAPTRRecord(Name name, int dclass, long ttl, int order, int preference,
+	    String flags, String service, String regexp, Name replacement)
+{
+	super(name, Type.NAPTR, dclass, ttl);
+	this.order = checkU16("order", order);
+	this.preference = checkU16("preference", preference);
+	try {
+		this.flags = byteArrayFromString(flags);
+		this.service = byteArrayFromString(service);
+		this.regexp = byteArrayFromString(regexp);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException(e.getMessage());
+	}
+	this.replacement = checkName("replacement", replacement);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	order = in.readU16();
+	preference = in.readU16();
+	flags = in.readCountedString();
+	service = in.readCountedString();
+	regexp = in.readCountedString();
+	replacement = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	order = st.getUInt16();
+	preference = st.getUInt16();
+	try {
+		flags = byteArrayFromString(st.getString());
+		service = byteArrayFromString(st.getString());
+		regexp = byteArrayFromString(st.getString());
+	}
+	catch (TextParseException e) {
+		throw st.exception(e.getMessage());
+	}
+	replacement = st.getName(origin);
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(order);
+	sb.append(" ");
+	sb.append(preference);
+	sb.append(" ");
+	sb.append(byteArrayToString(flags, true));
+	sb.append(" ");
+	sb.append(byteArrayToString(service, true));
+	sb.append(" ");
+	sb.append(byteArrayToString(regexp, true));
+	sb.append(" ");
+	sb.append(replacement);
+	return sb.toString();
+}
+
+/** Returns the order */
+public int
+getOrder() {
+	return order;
+}
+
+/** Returns the preference */
+public int
+getPreference() {
+	return preference;
+}
+
+/** Returns flags */
+public String
+getFlags() {
+	return byteArrayToString(flags, false);
+}
+
+/** Returns service */
+public String
+getService() {
+	return byteArrayToString(service, false);
+}
+
+/** Returns regexp */
+public String
+getRegexp() {
+	return byteArrayToString(regexp, false);
+}
+
+/** Returns the replacement domain-name */
+public Name
+getReplacement() {
+	return replacement;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(order);
+	out.writeU16(preference);
+	out.writeCountedString(flags);
+	out.writeCountedString(service);
+	out.writeCountedString(regexp);
+	replacement.toWire(out, null, canonical);
+}
+
+public Name
+getAdditionalName() {
+	return replacement;
+}
+
+}
diff --git a/src/org/xbill/DNS/NSAPRecord.java b/src/org/xbill/DNS/NSAPRecord.java
new file mode 100644
index 0000000..a6b2031
--- /dev/null
+++ b/src/org/xbill/DNS/NSAPRecord.java
@@ -0,0 +1,106 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * NSAP Address Record.
+ *
+ * @author Brian Wellington
+ */
+
+public class NSAPRecord extends Record {
+
+private static final long serialVersionUID = -1037209403185658593L;
+
+private byte [] address;
+
+NSAPRecord() {}
+
+Record
+getObject() {
+	return new NSAPRecord();
+}
+
+private static final byte []
+checkAndConvertAddress(String address) {
+	if (!address.substring(0, 2).equalsIgnoreCase("0x")) {
+		return null;
+	}
+	ByteArrayOutputStream bytes = new ByteArrayOutputStream();
+	boolean partial = false;
+	int current = 0;
+	for (int i = 2; i < address.length(); i++) {
+		char c = address.charAt(i);
+		if (c == '.') {
+			continue;
+		}
+		int value = Character.digit(c, 16);
+		if (value == -1) {
+			return null;
+		}
+		if (partial) {
+			current += value;
+			bytes.write(current);
+			partial = false;
+		} else {
+			current = value << 4;
+			partial = true;
+		}
+
+	}
+	if (partial) {
+		return null;
+	}
+	return bytes.toByteArray();
+}
+
+/**
+ * Creates an NSAP Record from the given data
+ * @param address The NSAP address.
+ * @throws IllegalArgumentException The address is not a valid NSAP address.
+ */
+public
+NSAPRecord(Name name, int dclass, long ttl, String address) {
+	super(name, Type.NSAP, dclass, ttl);
+	this.address = checkAndConvertAddress(address);
+	if (this.address == null) {
+		throw new IllegalArgumentException("invalid NSAP address " +
+						   address);
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	address = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String addr = st.getString();
+	this.address = checkAndConvertAddress(addr);
+	if (this.address == null)
+		throw st.exception("invalid NSAP address " + addr);
+}
+
+/**
+ * Returns the NSAP address.
+ */
+public String
+getAddress() {
+	return byteArrayToString(address, false);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(address);
+}
+
+String
+rrToString() {
+	return "0x" + base16.toString(address);
+}
+
+}
diff --git a/src/org/xbill/DNS/NSAP_PTRRecord.java b/src/org/xbill/DNS/NSAP_PTRRecord.java
new file mode 100644
index 0000000..ecc609f
--- /dev/null
+++ b/src/org/xbill/DNS/NSAP_PTRRecord.java
@@ -0,0 +1,38 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * NSAP Pointer Record  - maps a domain name representing an NSAP Address to
+ * a hostname.
+ *
+ * @author Brian Wellington
+ */
+
+public class NSAP_PTRRecord extends SingleNameBase {
+
+private static final long serialVersionUID = 2386284746382064904L;
+
+NSAP_PTRRecord() {}
+
+Record
+getObject() {
+	return new NSAP_PTRRecord();
+}
+
+/** 
+ * Creates a new NSAP_PTR Record with the given data
+ * @param target The name of the host with this address
+ */
+public
+NSAP_PTRRecord(Name name, int dclass, long ttl, Name target) {
+	super(name, Type.NSAP_PTR, dclass, ttl, target, "target");
+}
+
+/** Gets the target of the NSAP_PTR Record */
+public Name
+getTarget() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/NSEC3PARAMRecord.java b/src/org/xbill/DNS/NSEC3PARAMRecord.java
new file mode 100644
index 0000000..d663a62
--- /dev/null
+++ b/src/org/xbill/DNS/NSEC3PARAMRecord.java
@@ -0,0 +1,165 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.IOException;
+import java.security.NoSuchAlgorithmException;
+
+import org.xbill.DNS.utils.base16;
+
+/**
+ * Next SECure name 3 Parameters - this record contains the parameters (hash
+ * algorithm, salt, iterations) used for a valid, complete NSEC3 chain present
+ * in a zone. Zones signed using NSEC3 must include this record at the zone apex
+ * to inform authoritative servers that NSEC3 is being used with the given
+ * parameters.
+ * 
+ * @author Brian Wellington
+ * @author David Blacka
+ */
+
+public class NSEC3PARAMRecord extends Record {
+
+private static final long serialVersionUID = -8689038598776316533L;
+
+private int hashAlg;
+private int flags;
+private int iterations;
+private byte salt[];
+
+NSEC3PARAMRecord() {}
+
+Record getObject() {
+	return new NSEC3PARAMRecord();
+}
+
+/**
+ * Creates an NSEC3PARAM record from the given data.
+ * 
+ * @param name The ownername of the NSEC3PARAM record (generally the zone name).
+ * @param dclass The class.
+ * @param ttl The TTL.
+ * @param hashAlg The hash algorithm.
+ * @param flags The value of the flags field.
+ * @param iterations The number of hash iterations.
+ * @param salt The salt to use (may be null).
+ */
+public NSEC3PARAMRecord(Name name, int dclass, long ttl, int hashAlg, 
+			int flags, int iterations, byte [] salt)
+{
+	super(name, Type.NSEC3PARAM, dclass, ttl);
+	this.hashAlg = checkU8("hashAlg", hashAlg);
+	this.flags = checkU8("flags", flags);
+	this.iterations = checkU16("iterations", iterations);
+
+	if (salt != null) {
+		if (salt.length > 255)
+			throw new IllegalArgumentException("Invalid salt " +
+							   "length");
+		if (salt.length > 0) {
+			this.salt = new byte[salt.length];
+			System.arraycopy(salt, 0, this.salt, 0, salt.length);
+		}
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	hashAlg = in.readU8();
+	flags = in.readU8();
+	iterations = in.readU16();
+
+	int salt_length = in.readU8();
+	if (salt_length > 0)
+		salt = in.readByteArray(salt_length);
+	else
+		salt = null;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(hashAlg);
+	out.writeU8(flags);
+	out.writeU16(iterations);
+
+	if (salt != null) {
+		out.writeU8(salt.length);
+		out.writeByteArray(salt);
+	} else
+		out.writeU8(0);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException
+{
+	hashAlg = st.getUInt8();
+	flags = st.getUInt8();
+	iterations = st.getUInt16();
+
+	String s = st.getString();
+	if (s.equals("-"))
+		salt = null;
+	else {
+		st.unget();
+		salt = st.getHexString();
+		if (salt.length > 255)
+			throw st.exception("salt value too long");
+	}
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(hashAlg);
+	sb.append(' ');
+	sb.append(flags);
+	sb.append(' ');
+	sb.append(iterations);
+	sb.append(' ');
+	if (salt == null)
+		sb.append('-');
+	else
+		sb.append(base16.toString(salt));
+
+	return sb.toString();
+}
+
+/** Returns the hash algorithm */
+public int
+getHashAlgorithm() {
+	return hashAlg;
+}
+
+/** Returns the flags */
+public int
+getFlags() {
+	return flags;
+}
+  
+/** Returns the number of iterations */
+public int
+getIterations() {
+	return iterations;
+}
+
+/** Returns the salt */
+public byte []
+getSalt()
+{
+	return salt;
+}
+
+/**
+ * Hashes a name with the parameters of this NSEC3PARAM record.
+ * @param name The name to hash
+ * @return The hashed version of the name
+ * @throws NoSuchAlgorithmException The hash algorithm is unknown.
+ */
+public byte []
+hashName(Name name) throws NoSuchAlgorithmException
+{
+	return NSEC3Record.hashName(name, hashAlg, iterations, salt);
+}
+
+}
diff --git a/src/org/xbill/DNS/NSEC3Record.java b/src/org/xbill/DNS/NSEC3Record.java
new file mode 100644
index 0000000..aa086b8
--- /dev/null
+++ b/src/org/xbill/DNS/NSEC3Record.java
@@ -0,0 +1,266 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.security.*;
+
+import org.xbill.DNS.utils.*;
+
+/**
+ * Next SECure name 3 - this record contains the next hashed name in an
+ * ordered list of hashed names in the zone, and a set of types for which
+ * records exist for this name. The presence of this record in a response
+ * signifies a negative response from a DNSSEC-signed zone.
+ * 
+ * This replaces the NSEC and NXT records, when used.
+ * 
+ * @author Brian Wellington
+ * @author David Blacka
+ */
+
+public class NSEC3Record extends Record {
+
+public static class Flags {
+	/**
+	 * NSEC3 flags identifiers.
+	 */
+
+	private Flags() {}
+
+	/** Unsigned delegation are not included in the NSEC3 chain.
+	 *
+	 */
+	public static final int OPT_OUT = 0x01;
+}
+
+public static class Digest {
+	private Digest() {}
+
+	/** SHA-1 */
+	public static final int SHA1 = 1;
+}
+
+public static final int SHA1_DIGEST_ID = Digest.SHA1;
+
+private static final long serialVersionUID = -7123504635968932855L;
+
+private int hashAlg;
+private int flags;
+private int iterations;
+private byte [] salt;
+private byte [] next;
+private TypeBitmap types;
+
+private static final base32 b32 = new base32(base32.Alphabet.BASE32HEX,
+					     false, false);
+
+NSEC3Record() {}
+
+Record getObject() {
+	return new NSEC3Record();
+}
+
+/**
+ * Creates an NSEC3 record from the given data.
+ * 
+ * @param name The ownername of the NSEC3 record (base32'd hash plus zonename).
+ * @param dclass The class.
+ * @param ttl The TTL.
+ * @param hashAlg The hash algorithm.
+ * @param flags The value of the flags field.
+ * @param iterations The number of hash iterations.
+ * @param salt The salt to use (may be null).
+ * @param next The next hash (may not be null).
+ * @param types The types present at the original ownername.
+ */
+public NSEC3Record(Name name, int dclass, long ttl, int hashAlg,
+		   int flags, int iterations, byte [] salt, byte [] next,
+		   int [] types)
+{
+	super(name, Type.NSEC3, dclass, ttl);
+	this.hashAlg = checkU8("hashAlg", hashAlg);
+	this.flags = checkU8("flags", flags);
+	this.iterations = checkU16("iterations", iterations);
+
+	if (salt != null) {
+		if (salt.length > 255)
+			throw new IllegalArgumentException("Invalid salt");
+		if (salt.length > 0) {
+			this.salt = new byte[salt.length];
+			System.arraycopy(salt, 0, this.salt, 0, salt.length);
+		}
+	}
+
+	if (next.length > 255) {
+		throw new IllegalArgumentException("Invalid next hash");
+	}
+	this.next = new byte[next.length];
+	System.arraycopy(next, 0, this.next, 0, next.length);
+	this.types = new TypeBitmap(types);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	hashAlg = in.readU8();
+	flags = in.readU8();
+	iterations = in.readU16();
+
+	int salt_length = in.readU8();
+	if (salt_length > 0)
+		salt = in.readByteArray(salt_length);
+	else
+		salt = null;
+
+	int next_length = in.readU8();
+	next = in.readByteArray(next_length);
+	types = new TypeBitmap(in);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(hashAlg);
+	out.writeU8(flags);
+	out.writeU16(iterations);
+
+	if (salt != null) {
+		out.writeU8(salt.length);
+		out.writeByteArray(salt);
+	} else
+		out.writeU8(0);
+
+	out.writeU8(next.length);
+	out.writeByteArray(next);
+	types.toWire(out);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	hashAlg = st.getUInt8();
+	flags = st.getUInt8();
+	iterations = st.getUInt16();
+
+	String s = st.getString();
+	if (s.equals("-"))
+		salt = null;
+	else {
+		st.unget();
+		salt = st.getHexString();
+		if (salt.length > 255)
+			throw st.exception("salt value too long");
+	}
+
+	next = st.getBase32String(b32);
+	types = new TypeBitmap(st);
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(hashAlg);
+	sb.append(' ');
+	sb.append(flags);
+	sb.append(' ');
+	sb.append(iterations);
+	sb.append(' ');
+	if (salt == null)
+		sb.append('-');
+	else
+		sb.append(base16.toString(salt));
+	sb.append(' ');
+	sb.append(b32.toString(next));
+
+	if (!types.empty()) {
+		sb.append(' ');
+		sb.append(types.toString());
+	}
+
+	return sb.toString();
+}
+
+/** Returns the hash algorithm */
+public int
+getHashAlgorithm() {
+	return hashAlg;
+}
+
+/** Returns the flags */
+public int
+getFlags() {
+	return flags;
+}
+
+/** Returns the number of iterations */
+public int
+getIterations() {
+	return iterations;
+}
+
+/** Returns the salt */
+public byte []
+getSalt()
+{
+	return salt;
+}
+
+/** Returns the next hash */
+public byte []
+getNext() {
+	return next;
+}
+
+  /** Returns the set of types defined for this name */
+public int []
+getTypes() {
+	return types.toArray();
+}
+
+/** Returns whether a specific type is in the set of types. */
+public boolean
+hasType(int type)
+{
+	return types.contains(type);
+}
+
+static byte []
+hashName(Name name, int hashAlg, int iterations, byte [] salt)
+throws NoSuchAlgorithmException
+{
+	MessageDigest digest;
+	switch (hashAlg) {
+	case Digest.SHA1:
+		digest = MessageDigest.getInstance("sha-1");
+		break;
+	default:
+		throw new NoSuchAlgorithmException("Unknown NSEC3 algorithm" +
+						   "identifier: " +
+						   hashAlg);
+	}
+	byte [] hash = null;
+	for (int i = 0; i <= iterations; i++) {
+		digest.reset();
+		if (i == 0)
+			digest.update(name.toWireCanonical());
+		else
+			digest.update(hash);
+		if (salt != null)
+			digest.update(salt);
+		hash = digest.digest();
+	}
+	return hash;
+}
+
+/**
+ * Hashes a name with the parameters of this NSEC3 record.
+ * @param name The name to hash
+ * @return The hashed version of the name
+ * @throws NoSuchAlgorithmException The hash algorithm is unknown.
+ */
+public byte []
+hashName(Name name) throws NoSuchAlgorithmException
+{
+	return hashName(name, hashAlg, iterations, salt);
+}
+
+}
diff --git a/src/org/xbill/DNS/NSECRecord.java b/src/org/xbill/DNS/NSECRecord.java
new file mode 100644
index 0000000..e523e37
--- /dev/null
+++ b/src/org/xbill/DNS/NSECRecord.java
@@ -0,0 +1,98 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Next SECure name - this record contains the following name in an
+ * ordered list of names in the zone, and a set of types for which
+ * records exist for this name.  The presence of this record in a response
+ * signifies a negative response from a DNSSEC-signed zone.
+ *
+ * This replaces the NXT record.
+ *
+ * @author Brian Wellington
+ * @author David Blacka
+ */
+
+public class NSECRecord extends Record {
+
+private static final long serialVersionUID = -5165065768816265385L;
+
+private Name next;
+private TypeBitmap types;
+
+NSECRecord() {}
+
+Record
+getObject() {
+	return new NSECRecord();
+}
+
+/**
+ * Creates an NSEC Record from the given data.
+ * @param next The following name in an ordered list of the zone
+ * @param types An array containing the types present.
+ */
+public
+NSECRecord(Name name, int dclass, long ttl, Name next, int [] types) {
+	super(name, Type.NSEC, dclass, ttl);
+	this.next = checkName("next", next);
+	for (int i = 0; i < types.length; i++) {
+		Type.check(types[i]);
+	}
+	this.types = new TypeBitmap(types);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	next = new Name(in);
+	types = new TypeBitmap(in);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	// Note: The next name is not lowercased.
+	next.toWire(out, null, false);
+	types.toWire(out);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	next = st.getName(origin);
+	types = new TypeBitmap(st);
+}
+
+/** Converts rdata to a String */
+String
+rrToString()
+{
+	StringBuffer sb = new StringBuffer();
+	sb.append(next);
+	if (!types.empty()) {
+		sb.append(' ');
+		sb.append(types.toString());
+	}
+	return sb.toString();
+}
+
+/** Returns the next name */
+public Name
+getNext() {
+	return next;
+}
+
+/** Returns the set of types defined for this name */
+public int []
+getTypes() {
+	return types.toArray();
+}
+
+/** Returns whether a specific type is in the set of types. */
+public boolean
+hasType(int type) {
+	return types.contains(type);
+}
+
+}
diff --git a/src/org/xbill/DNS/NSIDOption.java b/src/org/xbill/DNS/NSIDOption.java
new file mode 100644
index 0000000..7bcbcd5
--- /dev/null
+++ b/src/org/xbill/DNS/NSIDOption.java
@@ -0,0 +1,29 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * The Name Server Identifier Option, define in RFC 5001.
+ *
+ * @see OPTRecord
+ * 
+ * @author Brian Wellington
+ */
+public class NSIDOption extends GenericEDNSOption {
+
+private static final long serialVersionUID = 74739759292589056L;
+
+NSIDOption() {
+	super(EDNSOption.Code.NSID);
+}
+
+/**
+ * Construct an NSID option.
+ * @param data The contents of the option.
+ */
+public 
+NSIDOption(byte [] data) {
+	super(EDNSOption.Code.NSID, data);
+}
+
+}
diff --git a/src/org/xbill/DNS/NSRecord.java b/src/org/xbill/DNS/NSRecord.java
new file mode 100644
index 0000000..2908da4
--- /dev/null
+++ b/src/org/xbill/DNS/NSRecord.java
@@ -0,0 +1,42 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Name Server Record  - contains the name server serving the named zone
+ *
+ * @author Brian Wellington
+ */
+
+public class NSRecord extends SingleCompressedNameBase {
+
+private static final long serialVersionUID = 487170758138268838L;
+
+NSRecord() {}
+
+Record
+getObject() {
+	return new NSRecord();
+}
+
+/** 
+ * Creates a new NS Record with the given data
+ * @param target The name server for the given domain
+ */
+public
+NSRecord(Name name, int dclass, long ttl, Name target) {
+	super(name, Type.NS, dclass, ttl, target, "target");
+}
+
+/** Gets the target of the NS Record */
+public Name
+getTarget() {
+	return getSingleName();
+}
+
+public Name
+getAdditionalName() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/NULLRecord.java b/src/org/xbill/DNS/NULLRecord.java
new file mode 100644
index 0000000..fa46d61
--- /dev/null
+++ b/src/org/xbill/DNS/NULLRecord.java
@@ -0,0 +1,67 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * The NULL Record.  This has no defined purpose, but can be used to
+ * hold arbitrary data.
+ *
+ * @author Brian Wellington
+ */
+
+public class NULLRecord extends Record {
+
+private static final long serialVersionUID = -5796493183235216538L;
+
+private byte [] data;
+
+NULLRecord() {}
+
+Record
+getObject() {
+	return new NULLRecord();
+}
+
+/**
+ * Creates a NULL record from the given data.
+ * @param data The contents of the record.
+ */
+public
+NULLRecord(Name name, int dclass, long ttl, byte [] data) {
+	super(name, Type.NULL, dclass, ttl);
+
+	if (data.length > 0xFFFF) {
+		throw new IllegalArgumentException("data must be <65536 bytes");
+	}
+	this.data = data;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	data = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	throw st.exception("no defined text format for NULL records");
+}
+
+String
+rrToString() {
+	return unknownToString(data);
+}
+
+/** Returns the contents of this record. */
+public byte []
+getData() {
+	return data;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(data);
+}
+
+}
diff --git a/src/org/xbill/DNS/NXTRecord.java b/src/org/xbill/DNS/NXTRecord.java
new file mode 100644
index 0000000..ad04e01
--- /dev/null
+++ b/src/org/xbill/DNS/NXTRecord.java
@@ -0,0 +1,111 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * Next name - this record contains the following name in an ordered list
+ * of names in the zone, and a set of types for which records exist for
+ * this name.  The presence of this record in a response signifies a
+ * failed query for data in a DNSSEC-signed zone. 
+ *
+ * @author Brian Wellington
+ */
+
+public class NXTRecord extends Record {
+
+private static final long serialVersionUID = -8851454400765507520L;
+
+private Name next;
+private BitSet bitmap;
+
+NXTRecord() {}
+
+Record
+getObject() {
+	return new NXTRecord();
+}
+
+/**
+ * Creates an NXT Record from the given data
+ * @param next The following name in an ordered list of the zone
+ * @param bitmap The set of type for which records exist at this name
+*/
+public
+NXTRecord(Name name, int dclass, long ttl, Name next, BitSet bitmap) {
+	super(name, Type.NXT, dclass, ttl);
+	this.next = checkName("next", next);
+	this.bitmap = bitmap;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	next = new Name(in);
+	bitmap = new BitSet();
+	int bitmapLength = in.remaining();
+	for (int i = 0; i < bitmapLength; i++) {
+		int t = in.readU8();
+		for (int j = 0; j < 8; j++)
+			if ((t & (1 << (7 - j))) != 0)
+				bitmap.set(i * 8 + j);
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	next = st.getName(origin);
+	bitmap = new BitSet();
+	while (true) {
+		Tokenizer.Token t = st.get();
+		if (!t.isString())
+			break;
+		int typecode = Type.value(t.value, true);
+		if (typecode <= 0 || typecode > 128)
+			throw st.exception("Invalid type: " + t.value);
+		bitmap.set(typecode);
+	}
+	st.unget();
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(next);
+	int length = bitmap.length();
+	for (short i = 0; i < length; i++)
+		if (bitmap.get(i)) {
+			sb.append(" ");
+			sb.append(Type.string(i));
+		}
+	return sb.toString();
+}
+
+/** Returns the next name */
+public Name
+getNext() {
+	return next;
+}
+
+/** Returns the set of types defined for this name */
+public BitSet
+getBitmap() {
+	return bitmap;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	next.toWire(out, null, canonical);
+	int length = bitmap.length();
+	for (int i = 0, t = 0; i < length; i++) {
+		t |= (bitmap.get(i) ? (1 << (7 - i % 8)) : 0);
+		if (i % 8 == 7 || i == length - 1) {
+			out.writeU8(t);
+			t = 0;
+		}
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/Name.java b/src/org/xbill/DNS/Name.java
new file mode 100644
index 0000000..1331ad9
--- /dev/null
+++ b/src/org/xbill/DNS/Name.java
@@ -0,0 +1,822 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.text.*;
+
+/**
+ * A representation of a domain name.  It may either be absolute (fully
+ * qualified) or relative.
+ *
+ * @author Brian Wellington
+ */
+
+public class Name implements Comparable, Serializable {
+
+private static final long serialVersionUID = -7257019940971525644L;
+
+private static final int LABEL_NORMAL = 0;
+private static final int LABEL_COMPRESSION = 0xC0;
+private static final int LABEL_MASK = 0xC0;
+
+/* The name data */
+private byte [] name;
+
+/*
+ * Effectively an 8 byte array, where the low order byte stores the number
+ * of labels and the 7 higher order bytes store per-label offsets.
+ */
+private long offsets;
+
+/* Precomputed hashcode. */
+private int hashcode;
+
+private static final byte [] emptyLabel = new byte[] {(byte)0};
+private static final byte [] wildLabel = new byte[] {(byte)1, (byte)'*'};
+
+/** The root name */
+public static final Name root;
+
+/** The root name */
+public static final Name empty;
+
+/** The maximum length of a Name */
+private static final int MAXNAME = 255;
+
+/** The maximum length of a label a Name */
+private static final int MAXLABEL = 63;
+
+/** The maximum number of labels in a Name */
+private static final int MAXLABELS = 128;
+
+/** The maximum number of cached offsets */
+private static final int MAXOFFSETS = 7;
+
+/* Used for printing non-printable characters */
+private static final DecimalFormat byteFormat = new DecimalFormat();
+
+/* Used to efficiently convert bytes to lowercase */
+private static final byte lowercase[] = new byte[256];
+
+/* Used in wildcard names. */
+private static final Name wild;
+
+static {
+	byteFormat.setMinimumIntegerDigits(3);
+	for (int i = 0; i < lowercase.length; i++) {
+		if (i < 'A' || i > 'Z')
+			lowercase[i] = (byte)i;
+		else
+			lowercase[i] = (byte)(i - 'A' + 'a');
+	}
+	root = new Name();
+	root.appendSafe(emptyLabel, 0, 1);
+	empty = new Name();
+	empty.name = new byte[0];
+	wild = new Name();
+	wild.appendSafe(wildLabel, 0, 1);
+}
+
+private
+Name() {
+}
+
+private final void
+setoffset(int n, int offset) {
+	if (n >= MAXOFFSETS)
+		return;
+	int shift = 8 * (7 - n);
+	offsets &= (~(0xFFL << shift));
+	offsets |= ((long)offset << shift);
+}
+
+private final int
+offset(int n) {
+	if (n == 0 && getlabels() == 0)
+		return 0;
+	if (n < 0 || n >= getlabels())
+		throw new IllegalArgumentException("label out of range");
+	if (n < MAXOFFSETS) {
+		int shift = 8 * (7 - n);
+		return ((int)(offsets >>> shift) & 0xFF);
+	} else {
+		int pos = offset(MAXOFFSETS - 1);
+		for (int i = MAXOFFSETS - 1; i < n; i++)
+			pos += (name[pos] + 1);
+		return (pos);
+	}
+}
+
+private final void
+setlabels(int labels) {
+	offsets &= ~(0xFF);
+	offsets |= labels;
+}
+
+private final int
+getlabels() {
+	return (int)(offsets & 0xFF);
+}
+
+private static final void
+copy(Name src, Name dst) {
+	if (src.offset(0) == 0) {
+		dst.name = src.name;
+		dst.offsets = src.offsets;
+	} else {
+		int offset0 = src.offset(0);
+		int namelen = src.name.length - offset0;
+		int labels = src.labels();
+		dst.name = new byte[namelen];
+		System.arraycopy(src.name, offset0, dst.name, 0, namelen);
+		for (int i = 0; i < labels && i < MAXOFFSETS; i++)
+			dst.setoffset(i, src.offset(i) - offset0);
+		dst.setlabels(labels);
+	}
+}
+
+private final void
+append(byte [] array, int start, int n) throws NameTooLongException {
+	int length = (name == null ? 0 : (name.length - offset(0)));
+	int alength = 0;
+	for (int i = 0, pos = start; i < n; i++) {
+		int len = array[pos];
+		if (len > MAXLABEL)
+			throw new IllegalStateException("invalid label");
+		len++;
+		pos += len;
+		alength += len;
+	}
+	int newlength = length + alength;
+	if (newlength > MAXNAME)
+		throw new NameTooLongException();
+	int labels = getlabels();
+	int newlabels = labels + n;
+	if (newlabels > MAXLABELS)
+		throw new IllegalStateException("too many labels");
+	byte [] newname = new byte[newlength];
+	if (length != 0)
+		System.arraycopy(name, offset(0), newname, 0, length);
+	System.arraycopy(array, start, newname, length, alength);
+	name = newname;
+	for (int i = 0, pos = length; i < n; i++) {
+		setoffset(labels + i, pos);
+		pos += (newname[pos] + 1);
+	}
+	setlabels(newlabels);
+}
+
+private static TextParseException
+parseException(String str, String message) {
+	return new TextParseException("'" + str + "': " + message);
+}
+
+private final void
+appendFromString(String fullName, byte [] array, int start, int n)
+throws TextParseException
+{
+	try {
+		append(array, start, n);
+	}
+	catch (NameTooLongException e) {
+		throw parseException(fullName, "Name too long");
+	}
+}
+
+private final void
+appendSafe(byte [] array, int start, int n) {
+	try {
+		append(array, start, n);
+	}
+	catch (NameTooLongException e) {
+	}
+}
+
+/**
+ * Create a new name from a string and an origin.  This does not automatically
+ * make the name absolute; it will be absolute if it has a trailing dot or an
+ * absolute origin is appended.
+ * @param s The string to be converted
+ * @param origin If the name is not absolute, the origin to be appended.
+ * @throws TextParseException The name is invalid.
+ */
+public
+Name(String s, Name origin) throws TextParseException {
+	if (s.equals(""))
+		throw parseException(s, "empty name");
+	else if (s.equals("@")) {
+		if (origin == null)
+			copy(empty, this);
+		else
+			copy(origin, this);
+		return;
+	} else if (s.equals(".")) {
+		copy(root, this);
+		return;
+	}
+	int labelstart = -1;
+	int pos = 1;
+	byte [] label = new byte[MAXLABEL + 1];
+	boolean escaped = false;
+	int digits = 0;
+	int intval = 0;
+	boolean absolute = false;
+	for (int i = 0; i < s.length(); i++) {
+		byte b = (byte) s.charAt(i);
+		if (escaped) {
+			if (b >= '0' && b <= '9' && digits < 3) {
+				digits++;
+				intval *= 10;
+				intval += (b - '0');
+				if (intval > 255)
+					throw parseException(s, "bad escape");
+				if (digits < 3)
+					continue;
+				b = (byte) intval;
+			}
+			else if (digits > 0 && digits < 3)
+				throw parseException(s, "bad escape");
+			if (pos > MAXLABEL)
+				throw parseException(s, "label too long");
+			labelstart = pos;
+			label[pos++] = b;
+			escaped = false;
+		} else if (b == '\\') {
+			escaped = true;
+			digits = 0;
+			intval = 0;
+		} else if (b == '.') {
+			if (labelstart == -1)
+				throw parseException(s, "invalid empty label");
+			label[0] = (byte)(pos - 1);
+			appendFromString(s, label, 0, 1);
+			labelstart = -1;
+			pos = 1;
+		} else {
+			if (labelstart == -1)
+				labelstart = i;
+			if (pos > MAXLABEL)
+				throw parseException(s, "label too long");
+			label[pos++] = b;
+		}
+	}
+	if (digits > 0 && digits < 3)
+		throw parseException(s, "bad escape");
+	if (escaped)
+		throw parseException(s, "bad escape");
+	if (labelstart == -1) {
+		appendFromString(s, emptyLabel, 0, 1);
+		absolute = true;
+	} else {
+		label[0] = (byte)(pos - 1);
+		appendFromString(s, label, 0, 1);
+	}
+	if (origin != null && !absolute)
+		appendFromString(s, origin.name, 0, origin.getlabels());
+}
+
+/**
+ * Create a new name from a string.  This does not automatically make the name
+ * absolute; it will be absolute if it has a trailing dot.
+ * @param s The string to be converted
+ * @throws TextParseException The name is invalid.
+ */
+public
+Name(String s) throws TextParseException {
+	this(s, null);
+}
+
+/**
+ * Create a new name from a string and an origin.  This does not automatically
+ * make the name absolute; it will be absolute if it has a trailing dot or an
+ * absolute origin is appended.  This is identical to the constructor, except
+ * that it will avoid creating new objects in some cases.
+ * @param s The string to be converted
+ * @param origin If the name is not absolute, the origin to be appended.
+ * @throws TextParseException The name is invalid.
+ */
+public static Name
+fromString(String s, Name origin) throws TextParseException {
+	if (s.equals("@") && origin != null)
+		return origin;
+	else if (s.equals("."))
+		return (root);
+
+	return new Name(s, origin);
+}
+
+/**
+ * Create a new name from a string.  This does not automatically make the name
+ * absolute; it will be absolute if it has a trailing dot.  This is identical
+ * to the constructor, except that it will avoid creating new objects in some
+ * cases.
+ * @param s The string to be converted
+ * @throws TextParseException The name is invalid.
+ */
+public static Name
+fromString(String s) throws TextParseException {
+	return fromString(s, null);
+}
+
+/**
+ * Create a new name from a constant string.  This should only be used when
+ the name is known to be good - that is, when it is constant.
+ * @param s The string to be converted
+ * @throws IllegalArgumentException The name is invalid.
+ */
+public static Name
+fromConstantString(String s) {
+	try {
+		return fromString(s, null);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException("Invalid name '" + s + "'");
+	}
+}
+
+/**
+ * Create a new name from DNS a wire format message
+ * @param in A stream containing the DNS message which is currently
+ * positioned at the start of the name to be read.
+ */
+public
+Name(DNSInput in) throws WireParseException {
+	int len, pos;
+	boolean done = false;
+	byte [] label = new byte[MAXLABEL + 1];
+	boolean savedState = false;
+
+	while (!done) {
+		len = in.readU8();
+		switch (len & LABEL_MASK) {
+		case LABEL_NORMAL:
+			if (getlabels() >= MAXLABELS)
+				throw new WireParseException("too many labels");
+			if (len == 0) {
+				append(emptyLabel, 0, 1);
+				done = true;
+			} else {
+				label[0] = (byte)len;
+				in.readByteArray(label, 1, len);
+				append(label, 0, 1);
+			}
+			break;
+		case LABEL_COMPRESSION:
+			pos = in.readU8();
+			pos += ((len & ~LABEL_MASK) << 8);
+			if (Options.check("verbosecompression"))
+				System.err.println("currently " + in.current() +
+						   ", pointer to " + pos);
+
+			if (pos >= in.current() - 2)
+				throw new WireParseException("bad compression");
+			if (!savedState) {
+				in.save();
+				savedState = true;
+			}
+			in.jump(pos);
+			if (Options.check("verbosecompression"))
+				System.err.println("current name '" + this +
+						   "', seeking to " + pos);
+			break;
+		default:
+			throw new WireParseException("bad label type");
+		}
+	}
+	if (savedState) {
+		in.restore();
+	}
+}
+
+/**
+ * Create a new name from DNS wire format
+ * @param b A byte array containing the wire format of the name.
+ */
+public
+Name(byte [] b) throws IOException {
+	this(new DNSInput(b));
+}
+
+/**
+ * Create a new name by removing labels from the beginning of an existing Name
+ * @param src An existing Name
+ * @param n The number of labels to remove from the beginning in the copy
+ */
+public
+Name(Name src, int n) {
+	int slabels = src.labels();
+	if (n > slabels)
+		throw new IllegalArgumentException("attempted to remove too " +
+						   "many labels");
+	name = src.name;
+	setlabels(slabels - n);
+	for (int i = 0; i < MAXOFFSETS && i < slabels - n; i++)
+		setoffset(i, src.offset(i + n));
+}
+
+/**
+ * Creates a new name by concatenating two existing names.
+ * @param prefix The prefix name.
+ * @param suffix The suffix name.
+ * @return The concatenated name.
+ * @throws NameTooLongException The name is too long.
+ */
+public static Name
+concatenate(Name prefix, Name suffix) throws NameTooLongException {
+	if (prefix.isAbsolute())
+		return (prefix);
+	Name newname = new Name();
+	copy(prefix, newname);
+	newname.append(suffix.name, suffix.offset(0), suffix.getlabels());
+	return newname;
+}
+
+/**
+ * If this name is a subdomain of origin, return a new name relative to
+ * origin with the same value. Otherwise, return the existing name.
+ * @param origin The origin to remove.
+ * @return The possibly relativized name.
+ */
+public Name
+relativize(Name origin) {
+	if (origin == null || !subdomain(origin))
+		return this;
+	Name newname = new Name();
+	copy(this, newname);
+	int length = length() - origin.length();
+	int labels = newname.labels() - origin.labels();
+	newname.setlabels(labels);
+	newname.name = new byte[length];
+	System.arraycopy(name, offset(0), newname.name, 0, length);
+	return newname;
+}
+
+/**
+ * Generates a new Name with the first n labels replaced by a wildcard 
+ * @return The wildcard name
+ */
+public Name
+wild(int n) {
+	if (n < 1)
+		throw new IllegalArgumentException("must replace 1 or more " +
+						   "labels");
+	try {
+		Name newname = new Name();
+		copy(wild, newname);
+		newname.append(name, offset(n), getlabels() - n);
+		return newname;
+	}
+	catch (NameTooLongException e) {
+		throw new IllegalStateException
+					("Name.wild: concatenate failed");
+	}
+}
+
+/**
+ * Generates a new Name to be used when following a DNAME.
+ * @param dname The DNAME record to follow.
+ * @return The constructed name.
+ * @throws NameTooLongException The resulting name is too long.
+ */
+public Name
+fromDNAME(DNAMERecord dname) throws NameTooLongException {
+	Name dnameowner = dname.getName();
+	Name dnametarget = dname.getTarget();
+	if (!subdomain(dnameowner))
+		return null;
+
+	int plabels = labels() - dnameowner.labels();
+	int plength = length() - dnameowner.length();
+	int pstart = offset(0);
+
+	int dlabels = dnametarget.labels();
+	int dlength = dnametarget.length();
+
+	if (plength + dlength > MAXNAME)
+		throw new NameTooLongException();
+
+	Name newname = new Name();
+	newname.setlabels(plabels + dlabels);
+	newname.name = new byte[plength + dlength];
+	System.arraycopy(name, pstart, newname.name, 0, plength);
+	System.arraycopy(dnametarget.name, 0, newname.name, plength, dlength);
+
+	for (int i = 0, pos = 0; i < MAXOFFSETS && i < plabels + dlabels; i++) {
+		newname.setoffset(i, pos);
+		pos += (newname.name[pos] + 1);
+	}
+	return newname;
+}
+
+/**
+ * Is this name a wildcard?
+ */
+public boolean
+isWild() {
+	if (labels() == 0)
+		return false;
+	return (name[0] == (byte)1 && name[1] == (byte)'*');
+}
+
+/**
+ * Is this name absolute?
+ */
+public boolean
+isAbsolute() {
+	if (labels() == 0)
+		return false;
+	return (name[name.length - 1] == 0);
+}
+
+/**
+ * The length of the name.
+ */
+public short
+length() {
+	if (getlabels() == 0)
+		return 0;
+	return (short)(name.length - offset(0));
+}
+
+/**
+ * The number of labels in the name.
+ */
+public int
+labels() {
+	return getlabels();
+}
+
+/**
+ * Is the current Name a subdomain of the specified name?
+ */
+public boolean
+subdomain(Name domain) {
+	int labels = labels();
+	int dlabels = domain.labels();
+	if (dlabels > labels)
+		return false;
+	if (dlabels == labels)
+		return equals(domain);
+	return domain.equals(name, offset(labels - dlabels));
+}
+
+private String
+byteString(byte [] array, int pos) {
+	StringBuffer sb = new StringBuffer();
+	int len = array[pos++];
+	for (int i = pos; i < pos + len; i++) {
+		int b = array[i] & 0xFF;
+		if (b <= 0x20 || b >= 0x7f) {
+			sb.append('\\');
+			sb.append(byteFormat.format(b));
+		}
+		else if (b == '"' || b == '(' || b == ')' || b == '.' ||
+			 b == ';' || b == '\\' || b == '@' || b == '$')
+		{
+			sb.append('\\');
+			sb.append((char)b);
+		}
+		else
+			sb.append((char)b);
+	}
+	return sb.toString();
+}
+
+/**
+ * Convert a Name to a String
+ * @return The representation of this name as a (printable) String.
+ */
+public String
+toString() {
+	int labels = labels();
+	if (labels == 0)
+		return "@";
+	else if (labels == 1 && name[offset(0)] == 0)
+		return ".";
+	StringBuffer sb = new StringBuffer();
+	for (int i = 0, pos = offset(0); i < labels; i++) {
+		int len = name[pos];
+		if (len > MAXLABEL)
+			throw new IllegalStateException("invalid label");
+		if (len == 0)
+			break;
+		sb.append(byteString(name, pos));
+		sb.append('.');
+		pos += (1 + len);
+	}
+	if (!isAbsolute())
+		sb.deleteCharAt(sb.length() - 1);
+	return sb.toString();
+}
+
+/**
+ * Retrieve the nth label of a Name.  This makes a copy of the label; changing
+ * this does not change the Name.
+ * @param n The label to be retrieved.  The first label is 0.
+ */
+public byte []
+getLabel(int n) {
+	int pos = offset(n);
+	byte len = (byte)(name[pos] + 1);
+	byte [] label = new byte[len];
+	System.arraycopy(name, pos, label, 0, len);
+	return label;
+}
+
+/**
+ * Convert the nth label in a Name to a String
+ * @param n The label to be converted to a (printable) String.  The first
+ * label is 0.
+ */
+public String
+getLabelString(int n) {
+	int pos = offset(n);
+	return byteString(name, pos);
+}
+
+/**
+ * Emit a Name in DNS wire format
+ * @param out The output stream containing the DNS message.
+ * @param c The compression context, or null of no compression is desired.
+ * @throws IllegalArgumentException The name is not absolute.
+ */
+public void
+toWire(DNSOutput out, Compression c) {
+	if (!isAbsolute())
+		throw new IllegalArgumentException("toWire() called on " +
+						   "non-absolute name");
+	
+	int labels = labels();
+	for (int i = 0; i < labels - 1; i++) {
+		Name tname;
+		if (i == 0)
+			tname = this;
+		else
+			tname = new Name(this, i);
+		int pos = -1;
+		if (c != null)
+			pos = c.get(tname);
+		if (pos >= 0) {
+			pos |= (LABEL_MASK << 8);
+			out.writeU16(pos);
+			return;
+		} else {
+			if (c != null)
+				c.add(out.current(), tname);
+			int off = offset(i);
+			out.writeByteArray(name, off, name[off] + 1);
+		}
+	}
+	out.writeU8(0);
+}
+
+/**
+ * Emit a Name in DNS wire format
+ * @throws IllegalArgumentException The name is not absolute.
+ */
+public byte []
+toWire() {
+	DNSOutput out = new DNSOutput();
+	toWire(out, null);
+	return out.toByteArray();
+}
+
+/**
+ * Emit a Name in canonical DNS wire format (all lowercase)
+ * @param out The output stream to which the message is written.
+ */
+public void
+toWireCanonical(DNSOutput out) {
+	byte [] b = toWireCanonical();
+	out.writeByteArray(b);
+}
+
+/**
+ * Emit a Name in canonical DNS wire format (all lowercase)
+ * @return The canonical form of the name.
+ */
+public byte []
+toWireCanonical() {
+	int labels = labels();
+	if (labels == 0)
+		return (new byte[0]);
+	byte [] b = new byte[name.length - offset(0)];
+	for (int i = 0, spos = offset(0), dpos = 0; i < labels; i++) {
+		int len = name[spos];
+		if (len > MAXLABEL)
+			throw new IllegalStateException("invalid label");
+		b[dpos++] = name[spos++];
+		for (int j = 0; j < len; j++)
+			b[dpos++] = lowercase[(name[spos++] & 0xFF)];
+	}
+	return b;
+}
+
+/**
+ * Emit a Name in DNS wire format
+ * @param out The output stream containing the DNS message.
+ * @param c The compression context, or null of no compression is desired.
+ * @param canonical If true, emit the name in canonicalized form
+ * (all lowercase).
+ * @throws IllegalArgumentException The name is not absolute.
+ */
+public void
+toWire(DNSOutput out, Compression c, boolean canonical) {
+	if (canonical)
+		toWireCanonical(out);
+	else
+		toWire(out, c);
+}
+
+private final boolean
+equals(byte [] b, int bpos) {
+	int labels = labels();
+	for (int i = 0, pos = offset(0); i < labels; i++) {
+		if (name[pos] != b[bpos])
+			return false;
+		int len = name[pos++];
+		bpos++;
+		if (len > MAXLABEL)
+			throw new IllegalStateException("invalid label");
+		for (int j = 0; j < len; j++)
+			if (lowercase[(name[pos++] & 0xFF)] !=
+			    lowercase[(b[bpos++] & 0xFF)])
+				return false;
+	}
+	return true;
+}
+
+/**
+ * Are these two Names equivalent?
+ */
+public boolean
+equals(Object arg) {
+	if (arg == this)
+		return true;
+	if (arg == null || !(arg instanceof Name))
+		return false;
+	Name d = (Name) arg;
+	if (d.hashcode == 0)
+		d.hashCode();
+	if (hashcode == 0)
+		hashCode();
+	if (d.hashcode != hashcode)
+		return false;
+	if (d.labels() != labels())
+		return false;
+	return equals(d.name, d.offset(0));
+}
+
+/**
+ * Computes a hashcode based on the value
+ */
+public int
+hashCode() {
+	if (hashcode != 0)
+		return (hashcode);
+	int code = 0;
+	for (int i = offset(0); i < name.length; i++)
+		code += ((code << 3) + lowercase[(name[i] & 0xFF)]);
+	hashcode = code;
+	return hashcode;
+}
+
+/**
+ * Compares this Name to another Object.
+ * @param o The Object to be compared.
+ * @return The value 0 if the argument is a name equivalent to this name;
+ * a value less than 0 if the argument is less than this name in the canonical 
+ * ordering, and a value greater than 0 if the argument is greater than this
+ * name in the canonical ordering.
+ * @throws ClassCastException if the argument is not a Name.
+ */
+public int
+compareTo(Object o) {
+	Name arg = (Name) o;
+
+	if (this == arg)
+		return (0);
+
+	int labels = labels();
+	int alabels = arg.labels();
+	int compares = labels > alabels ? alabels : labels;
+
+	for (int i = 1; i <= compares; i++) {
+		int start = offset(labels - i);
+		int astart = arg.offset(alabels - i);
+		int length = name[start];
+		int alength = arg.name[astart];
+		for (int j = 0; j < length && j < alength; j++) {
+			int n = lowercase[(name[j + start + 1]) & 0xFF] -
+				lowercase[(arg.name[j + astart + 1]) & 0xFF];
+			if (n != 0)
+				return (n);
+		}
+		if (length != alength)
+			return (length - alength);
+	}
+	return (labels - alabels);
+}
+
+}
diff --git a/src/org/xbill/DNS/NameTooLongException.java b/src/org/xbill/DNS/NameTooLongException.java
new file mode 100644
index 0000000..114be39
--- /dev/null
+++ b/src/org/xbill/DNS/NameTooLongException.java
@@ -0,0 +1,24 @@
+// Copyright (c) 2002-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when a name is longer than the maximum length of a DNS
+ * name.
+ *
+ * @author Brian Wellington
+ */
+
+public class NameTooLongException extends WireParseException {
+
+public
+NameTooLongException() {
+	super();
+}
+
+public
+NameTooLongException(String s) {
+	super(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/OPTRecord.java b/src/org/xbill/DNS/OPTRecord.java
new file mode 100644
index 0000000..47fef2f
--- /dev/null
+++ b/src/org/xbill/DNS/OPTRecord.java
@@ -0,0 +1,191 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * Options - describes Extended DNS (EDNS) properties of a Message.
+ * No specific options are defined other than those specified in the
+ * header.  An OPT should be generated by Resolver.
+ *
+ * EDNS is a method to extend the DNS protocol while providing backwards
+ * compatibility and not significantly changing the protocol.  This
+ * implementation of EDNS is mostly complete at level 0.
+ *
+ * @see Message
+ * @see Resolver 
+ *
+ * @author Brian Wellington
+ */
+
+public class OPTRecord extends Record {
+
+private static final long serialVersionUID = -6254521894809367938L;
+
+private List options;
+
+OPTRecord() {}
+
+Record
+getObject() {
+	return new OPTRecord();
+}
+
+/**
+ * Creates an OPT Record.  This is normally called by SimpleResolver, but can
+ * also be called by a server.
+ * @param payloadSize The size of a packet that can be reassembled on the 
+ * sending host.
+ * @param xrcode The value of the extended rcode field.  This is the upper
+ * 16 bits of the full rcode.
+ * @param flags Additional message flags.
+ * @param version The EDNS version that this DNS implementation supports.
+ * This should be 0 for dnsjava.
+ * @param options The list of options that comprise the data field.  There
+ * are currently no defined options.
+ * @see ExtendedFlags
+ */
+public
+OPTRecord(int payloadSize, int xrcode, int version, int flags, List options) {
+	super(Name.root, Type.OPT, payloadSize, 0);
+	checkU16("payloadSize", payloadSize);
+	checkU8("xrcode", xrcode);
+	checkU8("version", version);
+	checkU16("flags", flags);
+	ttl = ((long)xrcode << 24) + ((long)version << 16) + flags;
+	if (options != null) {
+		this.options = new ArrayList(options);
+	}
+}
+
+/**
+ * Creates an OPT Record with no data.  This is normally called by
+ * SimpleResolver, but can also be called by a server.
+ * @param payloadSize The size of a packet that can be reassembled on the 
+ * sending host.
+ * @param xrcode The value of the extended rcode field.  This is the upper
+ * 16 bits of the full rcode.
+ * @param flags Additional message flags.
+ * @param version The EDNS version that this DNS implementation supports.
+ * This should be 0 for dnsjava.
+ * @see ExtendedFlags
+ */
+public
+OPTRecord(int payloadSize, int xrcode, int version, int flags) {
+	this(payloadSize, xrcode, version, flags, null);
+}
+
+/**
+ * Creates an OPT Record with no data.  This is normally called by
+ * SimpleResolver, but can also be called by a server.
+ */
+public
+OPTRecord(int payloadSize, int xrcode, int version) {
+	this(payloadSize, xrcode, version, 0, null);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	if (in.remaining() > 0)
+		options = new ArrayList();
+	while (in.remaining() > 0) {
+		EDNSOption option = EDNSOption.fromWire(in);
+		options.add(option);
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	throw st.exception("no text format defined for OPT");
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	if (options != null) {
+		sb.append(options);
+		sb.append(" ");
+	}
+	sb.append(" ; payload ");
+	sb.append(getPayloadSize());
+	sb.append(", xrcode ");
+	sb.append(getExtendedRcode());
+	sb.append(", version ");
+	sb.append(getVersion());
+	sb.append(", flags ");
+	sb.append(getFlags());
+	return sb.toString();
+}
+
+/** Returns the maximum allowed payload size. */
+public int
+getPayloadSize() {
+	return dclass;
+}
+
+/**
+ * Returns the extended Rcode
+ * @see Rcode
+ */
+public int
+getExtendedRcode() {
+	return (int)(ttl >>> 24);
+}
+
+/** Returns the highest supported EDNS version */
+public int
+getVersion() {
+	return (int)((ttl >>> 16) & 0xFF);
+}
+
+/** Returns the EDNS flags */
+public int
+getFlags() {
+	return (int)(ttl & 0xFFFF);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	if (options == null)
+		return;
+	Iterator it = options.iterator();
+	while (it.hasNext()) {
+		EDNSOption option = (EDNSOption) it.next();
+		option.toWire(out);
+	}
+}
+
+/**
+ * Gets all options in the OPTRecord.  This returns a list of EDNSOptions.
+ */
+public List
+getOptions() {
+	if (options == null)
+		return Collections.EMPTY_LIST;
+	return Collections.unmodifiableList(options);
+}
+
+/**
+ * Gets all options in the OPTRecord with a specific code.  This returns a list
+ * of EDNSOptions.
+ */
+public List
+getOptions(int code) {
+	if (options == null)
+		return Collections.EMPTY_LIST;
+	List list = Collections.EMPTY_LIST;
+	for (Iterator it = options.iterator(); it.hasNext(); ) {
+		EDNSOption opt = (EDNSOption) it.next();
+		if (opt.getCode() == code) {
+			if (list == Collections.EMPTY_LIST)
+				list = new ArrayList();
+			list.add(opt);
+		}
+	}
+	return list;
+}
+
+}
diff --git a/src/org/xbill/DNS/Opcode.java b/src/org/xbill/DNS/Opcode.java
new file mode 100644
index 0000000..dadbca1
--- /dev/null
+++ b/src/org/xbill/DNS/Opcode.java
@@ -0,0 +1,60 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to DNS opcodes
+ *
+ * @author Brian Wellington
+ */
+
+public final class Opcode {
+
+/** A standard query */
+public static final int QUERY		= 0;
+
+/** An inverse query (deprecated) */
+public static final int IQUERY		= 1;
+
+/** A server status request (not used) */
+public static final int STATUS		= 2;
+
+/**
+ * A message from a primary to a secondary server to initiate a zone transfer
+ */
+public static final int NOTIFY		= 4;
+
+/** A dynamic update message */
+public static final int UPDATE		= 5;
+
+private static Mnemonic opcodes = new Mnemonic("DNS Opcode",
+					       Mnemonic.CASE_UPPER);
+
+static {
+	opcodes.setMaximum(0xF);
+	opcodes.setPrefix("RESERVED");
+	opcodes.setNumericAllowed(true);
+
+	opcodes.add(QUERY, "QUERY");
+	opcodes.add(IQUERY, "IQUERY");
+	opcodes.add(STATUS, "STATUS");
+	opcodes.add(NOTIFY, "NOTIFY");
+	opcodes.add(UPDATE, "UPDATE");
+}
+
+private
+Opcode() {}
+
+/** Converts a numeric Opcode into a String */
+public static String
+string(int i) {
+	return opcodes.getText(i);
+}
+
+/** Converts a String representation of an Opcode into its numeric value */
+public static int
+value(String s) {
+	return opcodes.getValue(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/Options.java b/src/org/xbill/DNS/Options.java
new file mode 100644
index 0000000..2f1dae3
--- /dev/null
+++ b/src/org/xbill/DNS/Options.java
@@ -0,0 +1,123 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * Boolean options:<BR>
+ * bindttl - Print TTLs in BIND format<BR>
+ * multiline - Print records in multiline format<BR>
+ * noprintin - Don't print the class of a record if it's IN<BR>
+ * verbose - Turn on general debugging statements<BR>
+ * verbosemsg - Print all messages sent or received by SimpleResolver<BR>
+ * verbosecompression - Print messages related to name compression<BR>
+ * verbosesec - Print messages related to signature verification<BR>
+ * verbosecache - Print messages related to cache lookups<BR>
+ * <BR>
+ * Valued options:<BR>
+ * tsigfudge=n - Sets the default TSIG fudge value (in seconds)<BR>
+ * sig0validity=n - Sets the default SIG(0) validity period (in seconds)<BR>
+ *
+ * @author Brian Wellington
+ */
+
+public final class Options {
+
+private static Map table;
+
+static {
+	try {
+		refresh();
+	}
+	catch (SecurityException e) {
+	}
+}
+
+private
+Options() {}
+
+public static void
+refresh() {
+	String s = System.getProperty("dnsjava.options");
+	if (s != null) {
+		StringTokenizer st = new StringTokenizer(s, ",");
+		while (st.hasMoreTokens()) {
+			String token = st.nextToken();
+			int index = token.indexOf('=');
+			if (index == -1)
+				set(token);
+			else {
+				String option = token.substring(0, index);
+				String value = token.substring(index + 1);
+				set(option, value);
+			}
+		}
+	}
+}
+
+/** Clears all defined options */
+public static void
+clear() {
+	table = null;
+}
+
+/** Sets an option to "true" */
+public static void
+set(String option) {
+	if (table == null)
+		table = new HashMap();
+	table.put(option.toLowerCase(), "true");
+}
+
+/** Sets an option to the the supplied value */
+public static void
+set(String option, String value) {
+	if (table == null)
+		table = new HashMap();
+	table.put(option.toLowerCase(), value.toLowerCase());
+}
+
+/** Removes an option */
+public static void
+unset(String option) {
+	if (table == null)
+		return;
+	table.remove(option.toLowerCase());
+}
+
+/** Checks if an option is defined */
+public static boolean
+check(String option) {
+	if (table == null)
+		return false;
+	return (table.get(option.toLowerCase()) != null);
+}
+
+/** Returns the value of an option */
+public static String
+value(String option) {
+	if (table == null)
+		return null;
+	return ((String)table.get(option.toLowerCase()));
+}
+
+/**
+ * Returns the value of an option as an integer, or -1 if not defined.
+ */
+public static int
+intValue(String option) {
+	String s = value(option);
+	if (s != null) {
+		try {
+			int val = Integer.parseInt(s);
+			if (val > 0)
+				return (val);
+		}
+		catch (NumberFormatException e) {
+		}
+	}
+	return (-1);
+}
+
+}
diff --git a/src/org/xbill/DNS/PTRRecord.java b/src/org/xbill/DNS/PTRRecord.java
new file mode 100644
index 0000000..89be578
--- /dev/null
+++ b/src/org/xbill/DNS/PTRRecord.java
@@ -0,0 +1,38 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Pointer Record  - maps a domain name representing an Internet Address to
+ * a hostname.
+ *
+ * @author Brian Wellington
+ */
+
+public class PTRRecord extends SingleCompressedNameBase {
+
+private static final long serialVersionUID = -8321636610425434192L;
+
+PTRRecord() {}
+
+Record
+getObject() {
+	return new PTRRecord();
+}
+
+/** 
+ * Creates a new PTR Record with the given data
+ * @param target The name of the machine with this address
+ */
+public
+PTRRecord(Name name, int dclass, long ttl, Name target) {
+	super(name, Type.PTR, dclass, ttl, target, "target");
+}
+
+/** Gets the target of the PTR Record */
+public Name
+getTarget() {
+	return getSingleName();
+}
+
+}
diff --git a/src/org/xbill/DNS/PXRecord.java b/src/org/xbill/DNS/PXRecord.java
new file mode 100644
index 0000000..a407241
--- /dev/null
+++ b/src/org/xbill/DNS/PXRecord.java
@@ -0,0 +1,96 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * X.400 mail mapping record.
+ *
+ * @author Brian Wellington
+ */
+
+public class PXRecord extends Record {
+
+private static final long serialVersionUID = 1811540008806660667L;
+
+private int preference;
+private Name map822;
+private Name mapX400;
+
+PXRecord() {}
+
+Record
+getObject() {
+	return new PXRecord();
+}
+
+/**
+ * Creates an PX Record from the given data
+ * @param preference The preference of this mail address.
+ * @param map822 The RFC 822 component of the mail address.
+ * @param mapX400 The X.400 component of the mail address.
+ */
+public
+PXRecord(Name name, int dclass, long ttl, int preference,
+	 Name map822, Name mapX400)
+{
+	super(name, Type.PX, dclass, ttl);
+
+	this.preference = checkU16("preference", preference);
+	this.map822 = checkName("map822", map822);
+	this.mapX400 = checkName("mapX400", mapX400);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	preference = in.readU16();
+	map822 = new Name(in);
+	mapX400 = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	preference = st.getUInt16();
+	map822 = st.getName(origin);
+	mapX400 = st.getName(origin);
+}
+
+/** Converts the PX Record to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(preference);
+	sb.append(" ");
+	sb.append(map822);
+	sb.append(" ");
+	sb.append(mapX400);
+	return sb.toString();
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(preference);
+	map822.toWire(out, null, canonical);
+	mapX400.toWire(out, null, canonical);
+}
+
+/** Gets the preference of the route. */
+public int
+getPreference() {
+	return preference;
+}
+
+/** Gets the RFC 822 component of the mail address. */
+public Name
+getMap822() {
+	return map822;
+}
+
+/** Gets the X.400 component of the mail address. */
+public Name
+getMapX400() {
+	return mapX400;
+}
+
+}
diff --git a/src/org/xbill/DNS/RPRecord.java b/src/org/xbill/DNS/RPRecord.java
new file mode 100644
index 0000000..7aa066c
--- /dev/null
+++ b/src/org/xbill/DNS/RPRecord.java
@@ -0,0 +1,82 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Responsible Person Record - lists the mail address of a responsible person
+ * and a domain where TXT records are available.
+ *
+ * @author Tom Scola <tscola@research.att.com>
+ * @author Brian Wellington
+ */
+
+public class RPRecord extends Record {
+
+private static final long serialVersionUID = 8124584364211337460L;
+
+private Name mailbox;
+private Name textDomain;
+
+RPRecord() {}
+
+Record
+getObject() {
+	return new RPRecord();
+}
+
+/**
+ * Creates an RP Record from the given data
+ * @param mailbox The responsible person
+ * @param textDomain The address where TXT records can be found
+ */
+public
+RPRecord(Name name, int dclass, long ttl, Name mailbox, Name textDomain) {
+	super(name, Type.RP, dclass, ttl);
+
+	this.mailbox = checkName("mailbox", mailbox);
+	this.textDomain = checkName("textDomain", textDomain);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	mailbox = new Name(in);
+	textDomain = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	mailbox = st.getName(origin);
+	textDomain = st.getName(origin);
+}
+
+/** Converts the RP Record to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(mailbox);
+	sb.append(" ");
+	sb.append(textDomain);
+	return sb.toString();
+}
+
+/** Gets the mailbox address of the RP Record */
+public Name
+getMailbox() {
+	return mailbox;
+}
+
+/** Gets the text domain info of the RP Record */
+public Name
+getTextDomain() {
+	return textDomain;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	mailbox.toWire(out, null, canonical);
+	textDomain.toWire(out, null, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/RRSIGRecord.java b/src/org/xbill/DNS/RRSIGRecord.java
new file mode 100644
index 0000000..c092839
--- /dev/null
+++ b/src/org/xbill/DNS/RRSIGRecord.java
@@ -0,0 +1,50 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * Recource Record Signature - An RRSIG provides the digital signature of an
+ * RRset, so that the data can be authenticated by a DNSSEC-capable resolver.
+ * The signature is generated by a key contained in a DNSKEY Record.
+ * @see RRset
+ * @see DNSSEC
+ * @see KEYRecord
+ *
+ * @author Brian Wellington
+ */
+
+public class RRSIGRecord extends SIGBase {
+
+private static final long serialVersionUID = -2609150673537226317L;
+
+RRSIGRecord() {}
+
+Record
+getObject() {
+	return new RRSIGRecord();
+}
+
+/**
+ * Creates an RRSIG Record from the given data
+ * @param covered The RRset type covered by this signature
+ * @param alg The cryptographic algorithm of the key that generated the
+ * signature
+ * @param origttl The original TTL of the RRset
+ * @param expire The time at which the signature expires
+ * @param timeSigned The time at which this signature was generated
+ * @param footprint The footprint/key id of the signing key.
+ * @param signer The owner of the signing key
+ * @param signature Binary data representing the signature
+ */
+public
+RRSIGRecord(Name name, int dclass, long ttl, int covered, int alg, long origttl,
+	    Date expire, Date timeSigned, int footprint, Name signer,
+	    byte [] signature)
+{
+	super(name, Type.RRSIG, dclass, ttl, covered, alg, origttl, expire,
+	      timeSigned, footprint, signer, signature);
+}
+
+}
diff --git a/src/org/xbill/DNS/RRset.java b/src/org/xbill/DNS/RRset.java
new file mode 100644
index 0000000..fa1a6ad
--- /dev/null
+++ b/src/org/xbill/DNS/RRset.java
@@ -0,0 +1,258 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.Serializable;
+import java.util.*;
+
+/**
+ * A set of Records with the same name, type, and class.  Also included
+ * are all RRSIG records signing the data records.
+ * @see Record
+ * @see RRSIGRecord 
+ *
+ * @author Brian Wellington
+ */
+
+public class RRset implements Serializable {
+
+private static final long serialVersionUID = -3270249290171239695L;
+
+/*
+ * rrs contains both normal and RRSIG records, with the RRSIG records
+ * at the end.
+ */
+private List rrs;
+private short nsigs;
+private short position;
+
+/** Creates an empty RRset */
+public
+RRset() {
+	rrs = new ArrayList(1);
+	nsigs = 0;
+	position = 0;
+}
+
+/** Creates an RRset and sets its contents to the specified record */
+public
+RRset(Record record) {
+	this();
+	safeAddRR(record);
+}
+
+/** Creates an RRset with the contents of an existing RRset */
+public
+RRset(RRset rrset) {
+	synchronized (rrset) {
+		rrs = (List) ((ArrayList)rrset.rrs).clone();
+		nsigs = rrset.nsigs;
+		position = rrset.position;
+	}
+}
+
+private void
+safeAddRR(Record r) {
+	if (!(r instanceof RRSIGRecord)) {
+		if (nsigs == 0)
+			rrs.add(r);
+		else
+			rrs.add(rrs.size() - nsigs, r);
+	} else {
+		rrs.add(r);
+		nsigs++;
+	}
+}
+
+/** Adds a Record to an RRset */
+public synchronized void
+addRR(Record r) {
+	if (rrs.size() == 0) {
+		safeAddRR(r);
+		return;
+	}
+	Record first = first();
+	if (!r.sameRRset(first))
+		throw new IllegalArgumentException("record does not match " +
+						   "rrset");
+
+	if (r.getTTL() != first.getTTL()) {
+		if (r.getTTL() > first.getTTL()) {
+			r = r.cloneRecord();
+			r.setTTL(first.getTTL());
+		} else {
+			for (int i = 0; i < rrs.size(); i++) {
+				Record tmp = (Record) rrs.get(i);
+				tmp = tmp.cloneRecord();
+				tmp.setTTL(r.getTTL());
+				rrs.set(i, tmp);
+			}
+		}
+	}
+
+	if (!rrs.contains(r))
+		safeAddRR(r);
+}
+
+/** Deletes a Record from an RRset */
+public synchronized void
+deleteRR(Record r) {
+	if (rrs.remove(r) && (r instanceof RRSIGRecord))
+		nsigs--;
+}
+
+/** Deletes all Records from an RRset */
+public synchronized void
+clear() {
+	rrs.clear();
+	position = 0;
+	nsigs = 0;
+}
+
+private synchronized Iterator
+iterator(boolean data, boolean cycle) {
+	int size, start, total;
+
+	total = rrs.size();
+
+	if (data)
+		size = total - nsigs;
+	else
+		size = nsigs;
+	if (size == 0)
+		return Collections.EMPTY_LIST.iterator();
+
+	if (data) {
+		if (!cycle)
+			start = 0;
+		else {
+			if (position >= size)
+				position = 0;
+			start = position++;
+		}
+	} else {
+		start = total - nsigs;
+	}
+
+	List list = new ArrayList(size);
+	if (data) {
+		list.addAll(rrs.subList(start, size));
+		if (start != 0)
+			list.addAll(rrs.subList(0, start));
+	} else {
+		list.addAll(rrs.subList(start, total));
+	}
+
+	return list.iterator();
+}
+
+/**
+ * Returns an Iterator listing all (data) records.
+ * @param cycle If true, cycle through the records so that each Iterator will
+ * start with a different record.
+ */
+public synchronized Iterator
+rrs(boolean cycle) {
+	return iterator(true, cycle);
+}
+
+/**
+ * Returns an Iterator listing all (data) records.  This cycles through
+ * the records, so each Iterator will start with a different record.
+ */
+public synchronized Iterator
+rrs() {
+	return iterator(true, true);
+}
+
+/** Returns an Iterator listing all signature records */
+public synchronized Iterator
+sigs() {
+	return iterator(false, false);
+}
+
+/** Returns the number of (data) records */
+public synchronized int
+size() {
+	return rrs.size() - nsigs;
+}
+
+/**
+ * Returns the name of the records
+ * @see Name
+ */
+public Name
+getName() {
+	return first().getName();
+}
+
+/**
+ * Returns the type of the records
+ * @see Type
+ */
+public int
+getType() {
+	return first().getRRsetType();
+}
+
+/**
+ * Returns the class of the records
+ * @see DClass
+ */
+public int
+getDClass() {
+	return first().getDClass();
+}
+
+/** Returns the ttl of the records */
+public synchronized long
+getTTL() {
+	return first().getTTL();
+}
+
+/**
+ * Returns the first record
+ * @throws IllegalStateException if the rrset is empty
+ */
+public synchronized Record
+first() {
+	if (rrs.size() == 0)
+		throw new IllegalStateException("rrset is empty");
+	return (Record) rrs.get(0);
+}
+
+private String
+iteratorToString(Iterator it) {
+	StringBuffer sb = new StringBuffer();
+	while (it.hasNext()) {
+		Record rr = (Record) it.next();
+		sb.append("[");
+		sb.append(rr.rdataToString());
+		sb.append("]");
+		if (it.hasNext())
+			sb.append(" ");
+	}
+	return sb.toString();
+}
+
+/** Converts the RRset to a String */
+public String
+toString() {
+	if (rrs == null)
+		return ("{empty}");
+	StringBuffer sb = new StringBuffer();
+	sb.append("{ ");
+	sb.append(getName() + " ");
+	sb.append(getTTL() + " ");
+	sb.append(DClass.string(getDClass()) + " ");
+	sb.append(Type.string(getType()) + " ");
+	sb.append(iteratorToString(iterator(true, false)));
+	if (nsigs > 0) {
+		sb.append(" sigs: ");
+		sb.append(iteratorToString(iterator(false, false)));
+	}
+	sb.append(" }");
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/RTRecord.java b/src/org/xbill/DNS/RTRecord.java
new file mode 100644
index 0000000..549731e
--- /dev/null
+++ b/src/org/xbill/DNS/RTRecord.java
@@ -0,0 +1,48 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Route Through Record - lists a route preference and intermediate host.
+ *
+ * @author Brian Wellington
+ */
+
+public class RTRecord extends U16NameBase {
+
+private static final long serialVersionUID = -3206215651648278098L;
+
+RTRecord() {}
+
+Record
+getObject() {
+	return new RTRecord();
+}
+
+/**
+ * Creates an RT Record from the given data
+ * @param preference The preference of the route.  Smaller numbers indicate
+ * more preferred routes.
+ * @param intermediateHost The domain name of the host to use as a router.
+ */
+public
+RTRecord(Name name, int dclass, long ttl, int preference,
+	 Name intermediateHost)
+{
+	super(name, Type.RT, dclass, ttl, preference, "preference",
+	      intermediateHost, "intermediateHost");
+}
+
+/** Gets the preference of the route. */
+public int
+getPreference() {
+	return getU16Field();
+}
+
+/** Gets the host to use as a router. */
+public Name
+getIntermediateHost() {
+	return getNameField();
+}
+
+}
diff --git a/src/org/xbill/DNS/Rcode.java b/src/org/xbill/DNS/Rcode.java
new file mode 100644
index 0000000..7f0dd1f
--- /dev/null
+++ b/src/org/xbill/DNS/Rcode.java
@@ -0,0 +1,123 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to DNS rcodes (error values)
+ *
+ * @author Brian Wellington
+ */
+
+public final class Rcode {
+
+private static Mnemonic rcodes = new Mnemonic("DNS Rcode",
+					      Mnemonic.CASE_UPPER);
+
+private static Mnemonic tsigrcodes = new Mnemonic("TSIG rcode",
+						  Mnemonic.CASE_UPPER);
+
+/** No error */
+public static final int NOERROR		= 0;
+
+/** Format error */
+public static final int FORMERR		= 1;
+
+/** Server failure */
+public static final int SERVFAIL	= 2;
+
+/** The name does not exist */
+public static final int NXDOMAIN	= 3;
+
+/** The operation requested is not implemented */
+public static final int NOTIMP		= 4;
+
+/** Deprecated synonym for NOTIMP. */
+public static final int NOTIMPL		= 4;
+
+/** The operation was refused by the server */
+public static final int REFUSED		= 5;
+
+/** The name exists */
+public static final int YXDOMAIN	= 6;
+
+/** The RRset (name, type) exists */
+public static final int YXRRSET		= 7;
+
+/** The RRset (name, type) does not exist */
+public static final int NXRRSET		= 8;
+
+/** The requestor is not authorized to perform this operation */
+public static final int NOTAUTH		= 9;
+
+/** The zone specified is not a zone */
+public static final int NOTZONE		= 10;
+
+/* EDNS extended rcodes */
+/** Unsupported EDNS level */
+public static final int BADVERS		= 16;
+
+/* TSIG/TKEY only rcodes */
+/** The signature is invalid (TSIG/TKEY extended error) */
+public static final int BADSIG		= 16;
+
+/** The key is invalid (TSIG/TKEY extended error) */
+public static final int BADKEY		= 17;
+
+/** The time is out of range (TSIG/TKEY extended error) */
+public static final int BADTIME		= 18;
+
+/** The mode is invalid (TKEY extended error) */
+public static final int BADMODE		= 19;
+
+static {
+	rcodes.setMaximum(0xFFF);
+	rcodes.setPrefix("RESERVED");
+	rcodes.setNumericAllowed(true);
+
+	rcodes.add(NOERROR, "NOERROR");
+	rcodes.add(FORMERR, "FORMERR");
+	rcodes.add(SERVFAIL, "SERVFAIL");
+	rcodes.add(NXDOMAIN, "NXDOMAIN");
+	rcodes.add(NOTIMP, "NOTIMP");
+	rcodes.addAlias(NOTIMP, "NOTIMPL");
+	rcodes.add(REFUSED, "REFUSED");
+	rcodes.add(YXDOMAIN, "YXDOMAIN");
+	rcodes.add(YXRRSET, "YXRRSET");
+	rcodes.add(NXRRSET, "NXRRSET");
+	rcodes.add(NOTAUTH, "NOTAUTH");
+	rcodes.add(NOTZONE, "NOTZONE");
+	rcodes.add(BADVERS, "BADVERS");
+
+	tsigrcodes.setMaximum(0xFFFF);
+	tsigrcodes.setPrefix("RESERVED");
+	tsigrcodes.setNumericAllowed(true);
+	tsigrcodes.addAll(rcodes);
+
+	tsigrcodes.add(BADSIG, "BADSIG");
+	tsigrcodes.add(BADKEY, "BADKEY");
+	tsigrcodes.add(BADTIME, "BADTIME");
+	tsigrcodes.add(BADMODE, "BADMODE");
+}
+
+private
+Rcode() {}
+
+/** Converts a numeric Rcode into a String */
+public static String
+string(int i) {
+	return rcodes.getText(i);
+}
+
+/** Converts a numeric TSIG extended Rcode into a String */
+public static String
+TSIGstring(int i) {
+	return tsigrcodes.getText(i);
+}
+
+/** Converts a String representation of an Rcode into its numeric value */
+public static int
+value(String s) {
+	return rcodes.getValue(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/Record.java b/src/org/xbill/DNS/Record.java
new file mode 100644
index 0000000..8da7015
--- /dev/null
+++ b/src/org/xbill/DNS/Record.java
@@ -0,0 +1,736 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.text.*;
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * A generic DNS resource record.  The specific record types extend this class.
+ * A record contains a name, type, class, ttl, and rdata.
+ *
+ * @author Brian Wellington
+ */
+
+public abstract class Record implements Cloneable, Comparable, Serializable {
+
+private static final long serialVersionUID = 2694906050116005466L;
+
+protected Name name;
+protected int type, dclass;
+protected long ttl;
+
+private static final DecimalFormat byteFormat = new DecimalFormat();
+
+static {
+	byteFormat.setMinimumIntegerDigits(3);
+}
+
+protected
+Record() {}
+
+Record(Name name, int type, int dclass, long ttl) {
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	Type.check(type);
+	DClass.check(dclass);
+	TTL.check(ttl);
+	this.name = name;
+	this.type = type;
+	this.dclass = dclass;
+	this.ttl = ttl;
+}
+
+/**
+ * Creates an empty record of the correct type; must be overriden
+ */
+abstract Record
+getObject();
+
+private static final Record
+getEmptyRecord(Name name, int type, int dclass, long ttl, boolean hasData) {
+	Record proto, rec;
+
+	if (hasData) {
+		proto = Type.getProto(type);
+		if (proto != null)
+			rec = proto.getObject();
+		else
+			rec = new UNKRecord();
+	} else
+		rec = new EmptyRecord();
+	rec.name = name;
+	rec.type = type;
+	rec.dclass = dclass;
+	rec.ttl = ttl;
+	return rec;
+}
+
+/**
+ * Converts the type-specific RR to wire format - must be overriden
+ */
+abstract void
+rrFromWire(DNSInput in) throws IOException;
+
+private static Record
+newRecord(Name name, int type, int dclass, long ttl, int length, DNSInput in)
+throws IOException
+{
+	Record rec;
+	rec = getEmptyRecord(name, type, dclass, ttl, in != null);
+	if (in != null) {
+		if (in.remaining() < length)
+			throw new WireParseException("truncated record");
+		in.setActive(length);
+
+		rec.rrFromWire(in);
+
+		if (in.remaining() > 0)
+			throw new WireParseException("invalid record length");
+		in.clearActive();
+	}
+	return rec;
+}
+
+/**
+ * Creates a new record, with the given parameters.
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @param ttl The record's time to live.
+ * @param length The length of the record's data.
+ * @param data The rdata of the record, in uncompressed DNS wire format.  Only
+ * the first length bytes are used.
+ */
+public static Record
+newRecord(Name name, int type, int dclass, long ttl, int length, byte [] data) {
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	Type.check(type);
+	DClass.check(dclass);
+	TTL.check(ttl);
+
+	DNSInput in;
+	if (data != null)
+		in = new DNSInput(data);
+	else
+		in = null;
+	try {
+		return newRecord(name, type, dclass, ttl, length, in);
+	}
+	catch (IOException e) {
+		return null;
+	}
+}
+
+/**
+ * Creates a new record, with the given parameters.
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @param ttl The record's time to live.
+ * @param data The complete rdata of the record, in uncompressed DNS wire
+ * format.
+ */
+public static Record
+newRecord(Name name, int type, int dclass, long ttl, byte [] data) {
+	return newRecord(name, type, dclass, ttl, data.length, data);
+}
+
+/**
+ * Creates a new empty record, with the given parameters.
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @param ttl The record's time to live.
+ * @return An object of a subclass of Record
+ */
+public static Record
+newRecord(Name name, int type, int dclass, long ttl) {
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	Type.check(type);
+	DClass.check(dclass);
+	TTL.check(ttl);
+
+	return getEmptyRecord(name, type, dclass, ttl, false);
+}
+
+/**
+ * Creates a new empty record, with the given parameters.  This method is
+ * designed to create records that will be added to the QUERY section
+ * of a message.
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @return An object of a subclass of Record
+ */
+public static Record
+newRecord(Name name, int type, int dclass) {
+	return newRecord(name, type, dclass, 0);
+}
+
+static Record
+fromWire(DNSInput in, int section, boolean isUpdate) throws IOException {
+	int type, dclass;
+	long ttl;
+	int length;
+	Name name;
+	Record rec;
+
+	name = new Name(in);
+	type = in.readU16();
+	dclass = in.readU16();
+
+	if (section == Section.QUESTION)
+		return newRecord(name, type, dclass);
+
+	ttl = in.readU32();
+	length = in.readU16();
+	if (length == 0 && isUpdate &&
+	    (section == Section.PREREQ || section == Section.UPDATE))
+		return newRecord(name, type, dclass, ttl);
+	rec = newRecord(name, type, dclass, ttl, length, in);
+	return rec;
+}
+
+static Record
+fromWire(DNSInput in, int section) throws IOException {
+	return fromWire(in, section, false);
+}
+
+/**
+ * Builds a Record from DNS uncompressed wire format.
+ */
+public static Record
+fromWire(byte [] b, int section) throws IOException {
+	return fromWire(new DNSInput(b), section, false);
+}
+
+void
+toWire(DNSOutput out, int section, Compression c) {
+	name.toWire(out, c);
+	out.writeU16(type);
+	out.writeU16(dclass);
+	if (section == Section.QUESTION)
+		return;
+	out.writeU32(ttl);
+	int lengthPosition = out.current();
+	out.writeU16(0); /* until we know better */
+	rrToWire(out, c, false);
+	int rrlength = out.current() - lengthPosition - 2;
+	out.writeU16At(rrlength, lengthPosition);
+}
+
+/**
+ * Converts a Record into DNS uncompressed wire format.
+ */
+public byte []
+toWire(int section) {
+	DNSOutput out = new DNSOutput();
+	toWire(out, section, null);
+	return out.toByteArray();
+}
+
+private void
+toWireCanonical(DNSOutput out, boolean noTTL) {
+	name.toWireCanonical(out);
+	out.writeU16(type);
+	out.writeU16(dclass);
+	if (noTTL) {
+		out.writeU32(0);
+	} else {
+		out.writeU32(ttl);
+	}
+	int lengthPosition = out.current();
+	out.writeU16(0); /* until we know better */
+	rrToWire(out, null, true);
+	int rrlength = out.current() - lengthPosition - 2;
+	out.writeU16At(rrlength, lengthPosition);
+}
+
+/*
+ * Converts a Record into canonical DNS uncompressed wire format (all names are
+ * converted to lowercase), optionally ignoring the TTL.
+ */
+private byte []
+toWireCanonical(boolean noTTL) {
+	DNSOutput out = new DNSOutput();
+	toWireCanonical(out, noTTL);
+	return out.toByteArray();
+}
+
+/**
+ * Converts a Record into canonical DNS uncompressed wire format (all names are
+ * converted to lowercase).
+ */
+public byte []
+toWireCanonical() {
+	return toWireCanonical(false);
+}
+
+/**
+ * Converts the rdata in a Record into canonical DNS uncompressed wire format
+ * (all names are converted to lowercase).
+ */
+public byte []
+rdataToWireCanonical() {
+	DNSOutput out = new DNSOutput();
+	rrToWire(out, null, true);
+	return out.toByteArray();
+}
+
+/**
+ * Converts the type-specific RR to text format - must be overriden
+ */
+abstract String rrToString();
+
+/**
+ * Converts the rdata portion of a Record into a String representation
+ */
+public String
+rdataToString() {
+	return rrToString();
+}
+
+/**
+ * Converts a Record into a String representation
+ */
+public String
+toString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(name);
+	if (sb.length() < 8)
+		sb.append("\t");
+	if (sb.length() < 16)
+		sb.append("\t");
+	sb.append("\t");
+	if (Options.check("BINDTTL"))
+		sb.append(TTL.format(ttl));
+	else
+		sb.append(ttl);
+	sb.append("\t");
+	if (dclass != DClass.IN || !Options.check("noPrintIN")) {
+		sb.append(DClass.string(dclass));
+		sb.append("\t");
+	}
+	sb.append(Type.string(type));
+	String rdata = rrToString();
+	if (!rdata.equals("")) {
+		sb.append("\t");
+		sb.append(rdata);
+	}
+	return sb.toString();
+}
+
+/**
+ * Converts the text format of an RR to the internal format - must be overriden
+ */
+abstract void
+rdataFromString(Tokenizer st, Name origin) throws IOException;
+
+/**
+ * Converts a String into a byte array.
+ */
+protected static byte []
+byteArrayFromString(String s) throws TextParseException {
+	byte [] array = s.getBytes();
+	boolean escaped = false;
+	boolean hasEscapes = false;
+
+	for (int i = 0; i < array.length; i++) {
+		if (array[i] == '\\') {
+			hasEscapes = true;
+			break;
+		}
+	}
+	if (!hasEscapes) {
+		if (array.length > 255) {
+			throw new TextParseException("text string too long");
+		}
+		return array;
+	}
+
+	ByteArrayOutputStream os = new ByteArrayOutputStream();
+
+	int digits = 0;
+	int intval = 0;
+	for (int i = 0; i < array.length; i++) {
+		byte b = array[i];
+		if (escaped) {
+			if (b >= '0' && b <= '9' && digits < 3) {
+				digits++; 
+				intval *= 10;
+				intval += (b - '0');
+				if (intval > 255)
+					throw new TextParseException
+								("bad escape");
+				if (digits < 3)
+					continue;
+				b = (byte) intval;
+			}
+			else if (digits > 0 && digits < 3)
+				throw new TextParseException("bad escape");
+			os.write(b);
+			escaped = false;
+		}
+		else if (array[i] == '\\') {
+			escaped = true;
+			digits = 0;
+			intval = 0;
+		}
+		else
+			os.write(array[i]);
+	}
+	if (digits > 0 && digits < 3)
+		throw new TextParseException("bad escape");
+	array = os.toByteArray();
+	if (array.length > 255) {
+		throw new TextParseException("text string too long");
+	}
+
+	return os.toByteArray();
+}
+
+/**
+ * Converts a byte array into a String.
+ */
+protected static String
+byteArrayToString(byte [] array, boolean quote) {
+	StringBuffer sb = new StringBuffer();
+	if (quote)
+		sb.append('"');
+	for (int i = 0; i < array.length; i++) {
+		int b = array[i] & 0xFF;
+		if (b < 0x20 || b >= 0x7f) {
+			sb.append('\\');
+			sb.append(byteFormat.format(b));
+		} else if (b == '"' || b == '\\') {
+			sb.append('\\');
+			sb.append((char)b);
+		} else
+			sb.append((char)b);
+	}
+	if (quote)
+		sb.append('"');
+	return sb.toString();
+}
+
+/**
+ * Converts a byte array into the unknown RR format.
+ */
+protected static String
+unknownToString(byte [] data) {
+	StringBuffer sb = new StringBuffer();
+	sb.append("\\# ");
+	sb.append(data.length);
+	sb.append(" ");
+	sb.append(base16.toString(data));
+	return sb.toString();
+}
+
+/**
+ * Builds a new Record from its textual representation
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @param ttl The record's time to live.
+ * @param st A tokenizer containing the textual representation of the rdata.
+ * @param origin The default origin to be appended to relative domain names.
+ * @return The new record
+ * @throws IOException The text format was invalid.
+ */
+public static Record
+fromString(Name name, int type, int dclass, long ttl, Tokenizer st, Name origin)
+throws IOException
+{
+	Record rec;
+
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	Type.check(type);
+	DClass.check(dclass);
+	TTL.check(ttl);
+
+	Tokenizer.Token t = st.get();
+	if (t.type == Tokenizer.IDENTIFIER && t.value.equals("\\#")) {
+		int length = st.getUInt16();
+		byte [] data = st.getHex();
+		if (data == null) {
+			data = new byte[0];
+		}
+		if (length != data.length)
+			throw st.exception("invalid unknown RR encoding: " +
+					   "length mismatch");
+		DNSInput in = new DNSInput(data);
+		return newRecord(name, type, dclass, ttl, length, in);
+	}
+	st.unget();
+	rec = getEmptyRecord(name, type, dclass, ttl, true);
+	rec.rdataFromString(st, origin);
+	t = st.get();
+	if (t.type != Tokenizer.EOL && t.type != Tokenizer.EOF) {
+		throw st.exception("unexpected tokens at end of record");
+	}
+	return rec;
+}
+
+/**
+ * Builds a new Record from its textual representation
+ * @param name The owner name of the record.
+ * @param type The record's type.
+ * @param dclass The record's class.
+ * @param ttl The record's time to live.
+ * @param s The textual representation of the rdata.
+ * @param origin The default origin to be appended to relative domain names.
+ * @return The new record
+ * @throws IOException The text format was invalid.
+ */
+public static Record
+fromString(Name name, int type, int dclass, long ttl, String s, Name origin)
+throws IOException
+{
+	return fromString(name, type, dclass, ttl, new Tokenizer(s), origin);
+}
+
+/**
+ * Returns the record's name
+ * @see Name
+ */
+public Name
+getName() {
+	return name;
+}
+
+/**
+ * Returns the record's type
+ * @see Type
+ */
+public int
+getType() {
+	return type;
+}
+
+/**
+ * Returns the type of RRset that this record would belong to.  For all types
+ * except RRSIG, this is equivalent to getType().
+ * @return The type of record, if not RRSIG.  If the type is RRSIG,
+ * the type covered is returned.
+ * @see Type
+ * @see RRset
+ * @see SIGRecord
+ */
+public int
+getRRsetType() {
+	if (type == Type.RRSIG) {
+		RRSIGRecord sig = (RRSIGRecord) this;
+		return sig.getTypeCovered();
+	}
+	return type;
+}
+
+/**
+ * Returns the record's class
+ */
+public int
+getDClass() {
+	return dclass;
+}
+
+/**
+ * Returns the record's TTL
+ */
+public long
+getTTL() {
+	return ttl;
+}
+
+/**
+ * Converts the type-specific RR to wire format - must be overriden
+ */
+abstract void
+rrToWire(DNSOutput out, Compression c, boolean canonical);
+
+/**
+ * Determines if two Records could be part of the same RRset.
+ * This compares the name, type, and class of the Records; the ttl and
+ * rdata are not compared.
+ */
+public boolean
+sameRRset(Record rec) {
+	return (getRRsetType() == rec.getRRsetType() &&
+		dclass == rec.dclass &&
+		name.equals(rec.name));
+}
+
+/**
+ * Determines if two Records are identical.  This compares the name, type,
+ * class, and rdata (with names canonicalized).  The TTLs are not compared.
+ * @param arg The record to compare to
+ * @return true if the records are equal, false otherwise.
+ */
+public boolean
+equals(Object arg) {
+	if (arg == null || !(arg instanceof Record))
+		return false;
+	Record r = (Record) arg;
+	if (type != r.type || dclass != r.dclass || !name.equals(r.name))
+		return false;
+	byte [] array1 = rdataToWireCanonical();
+	byte [] array2 = r.rdataToWireCanonical();
+	return Arrays.equals(array1, array2);
+}
+
+/**
+ * Generates a hash code based on the Record's data.
+ */
+public int
+hashCode() {
+	byte [] array = toWireCanonical(true);
+	int code = 0;
+	for (int i = 0; i < array.length; i++)
+		code += ((code << 3) + (array[i] & 0xFF));
+	return code;
+}
+
+Record
+cloneRecord() {
+	try {
+		return (Record) clone();
+	}
+	catch (CloneNotSupportedException e) {
+		throw new IllegalStateException();
+	}
+}
+
+/**
+ * Creates a new record identical to the current record, but with a different
+ * name.  This is most useful for replacing the name of a wildcard record.
+ */
+public Record
+withName(Name name) {
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	Record rec = cloneRecord();
+	rec.name = name;
+	return rec;
+}
+
+/**
+ * Creates a new record identical to the current record, but with a different
+ * class and ttl.  This is most useful for dynamic update.
+ */
+Record
+withDClass(int dclass, long ttl) {
+	Record rec = cloneRecord();
+	rec.dclass = dclass;
+	rec.ttl = ttl;
+	return rec;
+}
+
+/* Sets the TTL to the specified value.  This is intentionally not public. */
+void
+setTTL(long ttl) {
+	this.ttl = ttl;
+}
+
+/**
+ * Compares this Record to another Object.
+ * @param o The Object to be compared.
+ * @return The value 0 if the argument is a record equivalent to this record;
+ * a value less than 0 if the argument is less than this record in the
+ * canonical ordering, and a value greater than 0 if the argument is greater
+ * than this record in the canonical ordering.  The canonical ordering
+ * is defined to compare by name, class, type, and rdata.
+ * @throws ClassCastException if the argument is not a Record.
+ */
+public int
+compareTo(Object o) {
+	Record arg = (Record) o;
+
+	if (this == arg)
+		return (0);
+
+	int n = name.compareTo(arg.name);
+	if (n != 0)
+		return (n);
+	n = dclass - arg.dclass;
+	if (n != 0)
+		return (n);
+	n = type - arg.type;
+	if (n != 0)
+		return (n);
+	byte [] rdata1 = rdataToWireCanonical();
+	byte [] rdata2 = arg.rdataToWireCanonical();
+	for (int i = 0; i < rdata1.length && i < rdata2.length; i++) {
+		n = (rdata1[i] & 0xFF) - (rdata2[i] & 0xFF);
+		if (n != 0)
+			return (n);
+	}
+	return (rdata1.length - rdata2.length);
+}
+
+/**
+ * Returns the name for which additional data processing should be done
+ * for this record.  This can be used both for building responses and
+ * parsing responses.
+ * @return The name to used for additional data processing, or null if this
+ * record type does not require additional data processing.
+ */
+public Name
+getAdditionalName() {
+	return null;
+}
+
+/* Checks that an int contains an unsigned 8 bit value */
+static int
+checkU8(String field, int val) {
+	if (val < 0 || val > 0xFF)
+		throw new IllegalArgumentException("\"" + field + "\" " + val + 
+						   " must be an unsigned 8 " +
+						   "bit value");
+	return val;
+}
+
+/* Checks that an int contains an unsigned 16 bit value */
+static int
+checkU16(String field, int val) {
+	if (val < 0 || val > 0xFFFF)
+		throw new IllegalArgumentException("\"" + field + "\" " + val + 
+						   " must be an unsigned 16 " +
+						   "bit value");
+	return val;
+}
+
+/* Checks that a long contains an unsigned 32 bit value */
+static long
+checkU32(String field, long val) {
+	if (val < 0 || val > 0xFFFFFFFFL)
+		throw new IllegalArgumentException("\"" + field + "\" " + val + 
+						   " must be an unsigned 32 " +
+						   "bit value");
+	return val;
+}
+
+/* Checks that a name is absolute */
+static Name
+checkName(String field, Name name) {
+	if (!name.isAbsolute())
+		throw new RelativeNameException(name);
+	return name;
+}
+
+static byte []
+checkByteArrayLength(String field, byte [] array, int maxLength) {
+	if (array.length > 0xFFFF)
+		throw new IllegalArgumentException("\"" + field + "\" array " +
+						   "must have no more than " +
+						   maxLength + " elements");
+	byte [] out = new byte[array.length];
+	System.arraycopy(array, 0, out, 0, array.length);
+	return out;
+}
+
+}
diff --git a/src/org/xbill/DNS/RelativeNameException.java b/src/org/xbill/DNS/RelativeNameException.java
new file mode 100644
index 0000000..869fd39
--- /dev/null
+++ b/src/org/xbill/DNS/RelativeNameException.java
@@ -0,0 +1,24 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when a relative name is passed as an argument to
+ * a method requiring an absolute name.
+ *
+ * @author Brian Wellington
+ */
+
+public class RelativeNameException extends IllegalArgumentException {
+
+public
+RelativeNameException(Name name) {
+	super("'" + name + "' is not an absolute name");
+}
+
+public
+RelativeNameException(String s) {
+	super(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/ResolveThread.java b/src/org/xbill/DNS/ResolveThread.java
new file mode 100644
index 0000000..3087cdb
--- /dev/null
+++ b/src/org/xbill/DNS/ResolveThread.java
@@ -0,0 +1,45 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * A special-purpose thread used by Resolvers (both SimpleResolver and
+ * ExtendedResolver) to perform asynchronous queries.
+ *
+ * @author Brian Wellington
+ */
+
+class ResolveThread extends Thread {
+
+private Message query;
+private Object id;
+private ResolverListener listener;
+private Resolver res;
+
+/** Creates a new ResolveThread */
+public
+ResolveThread(Resolver res, Message query, Object id,
+	      ResolverListener listener)
+{
+	this.res = res;
+	this.query = query;
+	this.id = id;
+	this.listener = listener;
+}
+
+
+/**
+ * Performs the query, and executes the callback.
+ */
+public void
+run() {
+	try {
+		Message response = res.send(query);
+		listener.receiveMessage(id, response);
+	}
+	catch (Exception e) {
+		listener.handleException(id, e);
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/Resolver.java b/src/org/xbill/DNS/Resolver.java
new file mode 100644
index 0000000..7d28d40
--- /dev/null
+++ b/src/org/xbill/DNS/Resolver.java
@@ -0,0 +1,95 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * Interface describing a resolver.
+ *
+ * @author Brian Wellington
+ */
+
+public interface Resolver {
+
+/**
+ * Sets the port to communicate with on the server
+ * @param port The port to send messages to
+ */
+void setPort(int port);
+
+/**
+ * Sets whether TCP connections will be sent by default
+ * @param flag Indicates whether TCP connections are made
+ */
+void setTCP(boolean flag);
+
+/**
+ * Sets whether truncated responses will be ignored.  If not, a truncated
+ * response over UDP will cause a retransmission over TCP.
+ * @param flag Indicates whether truncated responses should be ignored.
+ */
+void setIgnoreTruncation(boolean flag);
+
+/**
+ * Sets the EDNS version used on outgoing messages.
+ * @param level The EDNS level to use.  0 indicates EDNS0 and -1 indicates no
+ * EDNS.
+ * @throws IllegalArgumentException An invalid level was indicated.
+ */
+void setEDNS(int level);
+
+/**
+ * Sets the EDNS information on outgoing messages.
+ * @param level The EDNS level to use.  0 indicates EDNS0 and -1 indicates no
+ * EDNS.
+ * @param payloadSize The maximum DNS packet size that this host is capable
+ * of receiving over UDP.  If 0 is specified, the default (1280) is used.
+ * @param flags EDNS extended flags to be set in the OPT record.
+ * @param options EDNS options to be set in the OPT record, specified as a
+ * List of OPTRecord.Option elements.
+ * @throws IllegalArgumentException An invalid field was specified.
+ * @see OPTRecord
+ */
+void setEDNS(int level, int payloadSize, int flags, List options);
+
+/**
+ * Specifies the TSIG key that messages will be signed with
+ * @param key The key
+ */
+void setTSIGKey(TSIG key);
+
+/**
+ * Sets the amount of time to wait for a response before giving up.
+ * @param secs The number of seconds to wait.
+ * @param msecs The number of milliseconds to wait.
+ */
+void setTimeout(int secs, int msecs);
+
+/**
+ * Sets the amount of time to wait for a response before giving up.
+ * @param secs The number of seconds to wait.
+ */
+void setTimeout(int secs);
+
+/**
+ * Sends a message and waits for a response.
+ * @param query The query to send.
+ * @return The response
+ * @throws IOException An error occurred while sending or receiving.
+ */
+Message send(Message query) throws IOException;
+
+/**
+ * Asynchronously sends a message registering a listener to receive a callback
+ * on success or exception.  Multiple asynchronous lookups can be performed
+ * in parallel.  Since the callback may be invoked before the function returns,
+ * external synchronization is necessary.
+ * @param query The query to send
+ * @param listener The object containing the callbacks.
+ * @return An identifier, which is also a parameter in the callback
+ */
+Object sendAsync(final Message query, final ResolverListener listener);
+
+}
diff --git a/src/org/xbill/DNS/ResolverConfig.java b/src/org/xbill/DNS/ResolverConfig.java
new file mode 100644
index 0000000..7b09daf
--- /dev/null
+++ b/src/org/xbill/DNS/ResolverConfig.java
@@ -0,0 +1,509 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.lang.reflect.*;
+import java.util.*;
+
+/**
+ * A class that tries to locate name servers and the search path to
+ * be appended to unqualified names.
+ *
+ * The following are attempted, in order, until one succeeds.
+ * <UL>
+ *   <LI>The properties 'dns.server' and 'dns.search' (comma delimited lists)
+ *       are checked.  The servers can either be IP addresses or hostnames
+ *       (which are resolved using Java's built in DNS support).
+ *   <LI>The sun.net.dns.ResolverConfiguration class is queried.
+ *   <LI>On Unix, /etc/resolv.conf is parsed.
+ *   <LI>On Windows, ipconfig/winipcfg is called and its output parsed.  This
+ *       may fail for non-English versions on Windows.
+ *   <LI>"localhost" is used as the nameserver, and the search path is empty.
+ * </UL>
+ *
+ * These routines will be called internally when creating Resolvers/Lookups
+ * without explicitly specifying server names, and can also be called
+ * directly if desired.
+ *
+ * @author Brian Wellington
+ * @author <a href="mailto:yannick@meudal.net">Yannick Meudal</a>
+ * @author <a href="mailto:arnt@gulbrandsen.priv.no">Arnt Gulbrandsen</a>
+ */
+
+public class ResolverConfig {
+
+private String [] servers = null;
+private Name [] searchlist = null;
+private int ndots = -1;
+
+private static ResolverConfig currentConfig;
+
+static {
+	refresh();
+}
+
+public
+ResolverConfig() {
+	if (findProperty())
+		return;
+	if (findSunJVM())
+		return;
+	if (servers == null || searchlist == null) {
+		String OS = System.getProperty("os.name");
+		String vendor = System.getProperty("java.vendor");
+		if (OS.indexOf("Windows") != -1) {
+			if (OS.indexOf("95") != -1 ||
+			    OS.indexOf("98") != -1 ||
+			    OS.indexOf("ME") != -1)
+				find95();
+			else
+				findNT();
+		} else if (OS.indexOf("NetWare") != -1) {
+			findNetware();
+		} else if (vendor.indexOf("Android") != -1) {
+			findAndroid();
+		} else {
+			findUnix();
+		}
+	}
+}
+
+private void
+addServer(String server, List list) {
+	if (list.contains(server))
+		return;
+	if (Options.check("verbose"))
+		System.out.println("adding server " + server);
+	list.add(server);
+}
+
+private void
+addSearch(String search, List list) {
+	Name name;
+	if (Options.check("verbose"))
+		System.out.println("adding search " + search);
+	try {
+		name = Name.fromString(search, Name.root);
+	}
+	catch (TextParseException e) {
+		return;
+	}
+	if (list.contains(name))
+		return;
+	list.add(name);
+}
+
+private int
+parseNdots(String token) {
+	token = token.substring(6);
+	try {
+		int ndots = Integer.parseInt(token);
+		if (ndots >= 0) {
+			if (Options.check("verbose"))
+				System.out.println("setting ndots " + token);
+			return ndots;
+		}
+	}
+	catch (NumberFormatException e) {
+	}
+	return -1;
+}
+
+private void
+configureFromLists(List lserver, List lsearch) {
+	if (servers == null && lserver.size() > 0)
+		servers = (String []) lserver.toArray(new String[0]);
+	if (searchlist == null && lsearch.size() > 0)
+		searchlist = (Name []) lsearch.toArray(new Name[0]);
+}
+
+private void
+configureNdots(int lndots) {
+	if (ndots < 0 && lndots > 0)
+		ndots = lndots;
+}
+
+/**
+ * Looks in the system properties to find servers and a search path.
+ * Servers are defined by dns.server=server1,server2...
+ * The search path is defined by dns.search=domain1,domain2...
+ */
+private boolean
+findProperty() {
+	String prop;
+	List lserver = new ArrayList(0);
+	List lsearch = new ArrayList(0);
+	StringTokenizer st;
+
+	prop = System.getProperty("dns.server");
+	if (prop != null) {
+		st = new StringTokenizer(prop, ",");
+		while (st.hasMoreTokens())
+			addServer(st.nextToken(), lserver);
+	}
+
+	prop = System.getProperty("dns.search");
+	if (prop != null) {
+		st = new StringTokenizer(prop, ",");
+		while (st.hasMoreTokens())
+			addSearch(st.nextToken(), lsearch);
+	}
+	configureFromLists(lserver, lsearch);
+	return (servers != null && searchlist != null);
+}
+
+/**
+ * Uses the undocumented Sun DNS implementation to determine the configuration.
+ * This doesn't work or even compile with all JVMs (gcj, for example).
+ */
+private boolean
+findSunJVM() {
+	List lserver = new ArrayList(0);
+	List lserver_tmp;
+	List lsearch = new ArrayList(0);
+	List lsearch_tmp;
+
+	try {
+		Class [] noClasses = new Class[0];
+		Object [] noObjects = new Object[0];
+		String resConfName = "sun.net.dns.ResolverConfiguration";
+		Class resConfClass = Class.forName(resConfName);
+		Object resConf;
+
+		// ResolverConfiguration resConf = ResolverConfiguration.open();
+		Method open = resConfClass.getDeclaredMethod("open", noClasses);
+		resConf = open.invoke(null, noObjects);
+
+		// lserver_tmp = resConf.nameservers();
+		Method nameservers = resConfClass.getMethod("nameservers",
+							    noClasses);
+		lserver_tmp = (List) nameservers.invoke(resConf, noObjects);
+
+		// lsearch_tmp = resConf.searchlist();
+		Method searchlist = resConfClass.getMethod("searchlist",
+							    noClasses);
+		lsearch_tmp = (List) searchlist.invoke(resConf, noObjects);
+	}
+	catch (Exception e) {
+		return false;
+	}
+
+	if (lserver_tmp.size() == 0)
+		return false;
+
+	if (lserver_tmp.size() > 0) {
+		Iterator it = lserver_tmp.iterator();
+		while (it.hasNext())
+			addServer((String) it.next(), lserver);
+	}
+
+	if (lsearch_tmp.size() > 0) {
+		Iterator it = lsearch_tmp.iterator();
+		while (it.hasNext())
+			addSearch((String) it.next(), lsearch);
+	}
+	configureFromLists(lserver, lsearch);
+	return true;
+}
+
+/**
+ * Looks in /etc/resolv.conf to find servers and a search path.
+ * "nameserver" lines specify servers.  "domain" and "search" lines
+ * define the search path.
+ */
+private void
+findResolvConf(String file) {
+	InputStream in = null;
+	try {
+		in = new FileInputStream(file);
+	}
+	catch (FileNotFoundException e) {
+		return;
+	}
+	InputStreamReader isr = new InputStreamReader(in);
+	BufferedReader br = new BufferedReader(isr);
+	List lserver = new ArrayList(0);
+	List lsearch = new ArrayList(0);
+	int lndots = -1;
+	try {
+		String line;
+		while ((line = br.readLine()) != null) {
+			if (line.startsWith("nameserver")) {
+				StringTokenizer st = new StringTokenizer(line);
+				st.nextToken(); /* skip nameserver */
+				addServer(st.nextToken(), lserver);
+			}
+			else if (line.startsWith("domain")) {
+				StringTokenizer st = new StringTokenizer(line);
+				st.nextToken(); /* skip domain */
+				if (!st.hasMoreTokens())
+					continue;
+				if (lsearch.isEmpty())
+					addSearch(st.nextToken(), lsearch);
+			}
+			else if (line.startsWith("search")) {
+				if (!lsearch.isEmpty())
+					lsearch.clear();
+				StringTokenizer st = new StringTokenizer(line);
+				st.nextToken(); /* skip search */
+				while (st.hasMoreTokens())
+					addSearch(st.nextToken(), lsearch);
+			}
+			else if(line.startsWith("options")) {
+				StringTokenizer st = new StringTokenizer(line);
+				st.nextToken(); /* skip options */
+				while (st.hasMoreTokens()) {
+					String token = st.nextToken();
+					if (token.startsWith("ndots:")) {
+						lndots = parseNdots(token);
+					}
+				}
+			}
+		}
+		br.close();
+	}
+	catch (IOException e) {
+	}
+
+	configureFromLists(lserver, lsearch);
+	configureNdots(lndots);
+}
+
+private void
+findUnix() {
+	findResolvConf("/etc/resolv.conf");
+}
+
+private void
+findNetware() {
+	findResolvConf("sys:/etc/resolv.cfg");
+}
+
+/**
+ * Parses the output of winipcfg or ipconfig.
+ */
+private void
+findWin(InputStream in, Locale locale) {
+	String packageName = ResolverConfig.class.getPackage().getName();
+	String resPackageName = packageName + ".windows.DNSServer";
+	ResourceBundle res;
+	if (locale != null)
+		res = ResourceBundle.getBundle(resPackageName, locale);
+	else
+		res = ResourceBundle.getBundle(resPackageName);
+
+	String host_name = res.getString("host_name");
+	String primary_dns_suffix = res.getString("primary_dns_suffix");
+	String dns_suffix = res.getString("dns_suffix");
+	String dns_servers = res.getString("dns_servers");
+
+	BufferedReader br = new BufferedReader(new InputStreamReader(in));
+	try {
+		List lserver = new ArrayList();
+		List lsearch = new ArrayList();
+		String line = null;
+		boolean readingServers = false;
+		boolean readingSearches = false;
+		while ((line = br.readLine()) != null) {
+			StringTokenizer st = new StringTokenizer(line);
+			if (!st.hasMoreTokens()) {
+				readingServers = false;
+				readingSearches = false;
+				continue;
+			}
+			String s = st.nextToken();
+			if (line.indexOf(":") != -1) {
+				readingServers = false;
+				readingSearches = false;
+			}
+			
+			if (line.indexOf(host_name) != -1) {
+				while (st.hasMoreTokens())
+					s = st.nextToken();
+				Name name;
+				try {
+					name = Name.fromString(s, null);
+				}
+				catch (TextParseException e) {
+					continue;
+				}
+				if (name.labels() == 1)
+					continue;
+				addSearch(s, lsearch);
+			} else if (line.indexOf(primary_dns_suffix) != -1) {
+				while (st.hasMoreTokens())
+					s = st.nextToken();
+				if (s.equals(":"))
+					continue;
+				addSearch(s, lsearch);
+				readingSearches = true;
+			} else if (readingSearches ||
+				   line.indexOf(dns_suffix) != -1)
+			{
+				while (st.hasMoreTokens())
+					s = st.nextToken();
+				if (s.equals(":"))
+					continue;
+				addSearch(s, lsearch);
+				readingSearches = true;
+			} else if (readingServers ||
+				   line.indexOf(dns_servers) != -1)
+			{
+				while (st.hasMoreTokens())
+					s = st.nextToken();
+				if (s.equals(":"))
+					continue;
+				addServer(s, lserver);
+				readingServers = true;
+			}
+		}
+		
+		configureFromLists(lserver, lsearch);
+	}
+	catch (IOException e) {
+	}
+	return;
+}
+
+private void
+findWin(InputStream in) {
+	String property = "org.xbill.DNS.windows.parse.buffer";
+	final int defaultBufSize = 8 * 1024;
+	int bufSize = Integer.getInteger(property, defaultBufSize).intValue();
+	BufferedInputStream b = new BufferedInputStream(in, bufSize);
+	b.mark(bufSize);
+	findWin(b, null);
+	if (servers == null) {
+		try {
+			b.reset();
+		} 
+		catch (IOException e) {
+			return;
+		}
+		findWin(b, new Locale("", ""));
+	}
+}
+
+/**
+ * Calls winipcfg and parses the result to find servers and a search path.
+ */
+private void
+find95() {
+	String s = "winipcfg.out";
+	try {
+		Process p;
+		p = Runtime.getRuntime().exec("winipcfg /all /batch " + s);
+		p.waitFor();
+		File f = new File(s);
+		findWin(new FileInputStream(f));
+		new File(s).delete();
+	}
+	catch (Exception e) {
+		return;
+	}
+}
+
+/**
+ * Calls ipconfig and parses the result to find servers and a search path.
+ */
+private void
+findNT() {
+	try {
+		Process p;
+		p = Runtime.getRuntime().exec("ipconfig /all");
+		findWin(p.getInputStream());
+		p.destroy();
+	}
+	catch (Exception e) {
+		return;
+	}
+}
+
+/**
+ * Parses the output of getprop, which is the only way to get DNS
+ * info on Android. getprop might disappear in future releases, so
+ * this code comes with a use-by date.
+ */
+private void
+findAndroid() {
+	// This originally looked for all lines containing .dns; but
+	// http://code.google.com/p/android/issues/detail?id=2207#c73
+	// indicates that net.dns* should always be the active nameservers, so
+	// we use those.
+	String re1 = "^\\d+(\\.\\d+){3}$";
+	String re2 = "^[0-9a-f]+(:[0-9a-f]*)+:[0-9a-f]+$";
+	try { 
+		ArrayList lserver = new ArrayList(); 
+		ArrayList lsearch = new ArrayList(); 
+		String line; 
+		Process p = Runtime.getRuntime().exec("getprop"); 
+		InputStream in = p.getInputStream();
+		InputStreamReader isr = new InputStreamReader(in);
+		BufferedReader br = new BufferedReader(isr);
+		while ((line = br.readLine()) != null ) { 
+			StringTokenizer t = new StringTokenizer(line, ":");
+			String name = t.nextToken();
+			if (name.indexOf( "net.dns" ) > -1) {
+				String v = t.nextToken();
+				v = v.replaceAll("[ \\[\\]]", "");
+				if ((v.matches(re1) || v.matches(re2)) &&
+				    !lserver.contains(v))
+					lserver.add(v);
+			}
+		}
+		configureFromLists(lserver, lsearch);
+	} catch ( Exception e ) { 
+		// ignore resolutely
+	}
+}
+
+/** Returns all located servers */
+public String []
+servers() {
+	return servers;
+}
+
+/** Returns the first located server */
+public String
+server() {
+	if (servers == null)
+		return null;
+	return servers[0];
+}
+
+/** Returns all entries in the located search path */
+public Name []
+searchPath() {
+	return searchlist;
+}
+
+/**
+ * Returns the located ndots value, or the default (1) if not configured.
+ * Note that ndots can only be configured in a resolv.conf file, and will only
+ * take effect if ResolverConfig uses resolv.conf directly (that is, if the
+ * JVM does not include the sun.net.dns.ResolverConfiguration class).
+ */
+public int
+ndots() {
+	if (ndots < 0)
+		return 1;
+	return ndots;
+}
+
+/** Gets the current configuration */
+public static synchronized ResolverConfig
+getCurrentConfig() {
+	return currentConfig;
+}
+
+/** Gets the current configuration */
+public static void
+refresh() {
+	ResolverConfig newConfig = new ResolverConfig();
+	synchronized (ResolverConfig.class) {
+		currentConfig = newConfig;
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/ResolverListener.java b/src/org/xbill/DNS/ResolverListener.java
new file mode 100644
index 0000000..accf82c
--- /dev/null
+++ b/src/org/xbill/DNS/ResolverListener.java
@@ -0,0 +1,30 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.EventListener;
+
+/**
+ * An interface to the asynchronous resolver.
+ * @see Resolver
+ *
+ * @author Brian Wellington
+ */
+
+public interface ResolverListener extends EventListener {
+
+/**
+ * The callback used by an asynchronous resolver
+ * @param id The identifier returned by Resolver.sendAsync()
+ * @param m The response message as returned by the Resolver
+ */
+void receiveMessage(Object id, Message m);
+
+/**
+ * The callback used by an asynchronous resolver when an exception is thrown
+ * @param id The identifier returned by Resolver.sendAsync()
+ * @param e The thrown exception
+ */
+void handleException(Object id, Exception e);
+
+}
diff --git a/src/org/xbill/DNS/ReverseMap.java b/src/org/xbill/DNS/ReverseMap.java
new file mode 100644
index 0000000..f4293de
--- /dev/null
+++ b/src/org/xbill/DNS/ReverseMap.java
@@ -0,0 +1,130 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.net.*;
+
+/**
+ * A set functions designed to deal with DNS names used in reverse mappings.
+ * For the IPv4 address a.b.c.d, the reverse map name is d.c.b.a.in-addr.arpa.
+ * For an IPv6 address, the reverse map name is ...ip6.arpa.
+ *
+ * @author Brian Wellington
+ */
+
+public final class ReverseMap {
+
+private static Name inaddr4 = Name.fromConstantString("in-addr.arpa.");
+private static Name inaddr6 = Name.fromConstantString("ip6.arpa.");
+
+/* Otherwise the class could be instantiated */
+private
+ReverseMap() {}
+
+/**
+ * Creates a reverse map name corresponding to an address contained in
+ * an array of 4 bytes (for an IPv4 address) or 16 bytes (for an IPv6 address).
+ * @param addr The address from which to build a name.
+ * @return The name corresponding to the address in the reverse map.
+ */
+public static Name
+fromAddress(byte [] addr) {
+	if (addr.length != 4 && addr.length != 16)
+		throw new IllegalArgumentException("array must contain " +
+						   "4 or 16 elements");
+
+	StringBuffer sb = new StringBuffer();
+	if (addr.length == 4) {
+		for (int i = addr.length - 1; i >= 0; i--) {
+			sb.append(addr[i] & 0xFF);
+			if (i > 0)
+				sb.append(".");
+		}
+	} else {
+		int [] nibbles = new int[2];
+		for (int i = addr.length - 1; i >= 0; i--) {
+			nibbles[0] = (addr[i] & 0xFF) >> 4;
+			nibbles[1] = (addr[i] & 0xFF) & 0xF;
+			for (int j = nibbles.length - 1; j >= 0; j--) {
+				sb.append(Integer.toHexString(nibbles[j]));
+				if (i > 0 || j > 0)
+					sb.append(".");
+			}
+		}
+	}
+
+	try {
+		if (addr.length == 4)
+			return Name.fromString(sb.toString(), inaddr4);
+		else
+			return Name.fromString(sb.toString(), inaddr6);
+	}
+	catch (TextParseException e) {
+		throw new IllegalStateException("name cannot be invalid");
+	}
+}
+
+/**
+ * Creates a reverse map name corresponding to an address contained in
+ * an array of 4 integers between 0 and 255 (for an IPv4 address) or 16
+ * integers between 0 and 255 (for an IPv6 address).
+ * @param addr The address from which to build a name.
+ * @return The name corresponding to the address in the reverse map.
+ */
+public static Name
+fromAddress(int [] addr) {
+	byte [] bytes = new byte[addr.length];
+	for (int i = 0; i < addr.length; i++) {
+		if (addr[i] < 0 || addr[i] > 0xFF)
+			throw new IllegalArgumentException("array must " +
+							   "contain values " +
+							   "between 0 and 255");
+		bytes[i] = (byte) addr[i];
+	}
+	return fromAddress(bytes);
+}
+
+/**
+ * Creates a reverse map name corresponding to an address contained in
+ * an InetAddress.
+ * @param addr The address from which to build a name.
+ * @return The name corresponding to the address in the reverse map.
+ */
+public static Name
+fromAddress(InetAddress addr) {
+	return fromAddress(addr.getAddress());
+}
+
+/**
+ * Creates a reverse map name corresponding to an address contained in
+ * a String.
+ * @param addr The address from which to build a name.
+ * @return The name corresponding to the address in the reverse map.
+ * @throws UnknownHostException The string does not contain a valid address.
+ */
+public static Name
+fromAddress(String addr, int family) throws UnknownHostException {
+	byte [] array = Address.toByteArray(addr, family);
+	if (array == null)
+		throw new UnknownHostException("Invalid IP address");
+	return fromAddress(array);
+}
+
+/**
+ * Creates a reverse map name corresponding to an address contained in
+ * a String.
+ * @param addr The address from which to build a name.
+ * @return The name corresponding to the address in the reverse map.
+ * @throws UnknownHostException The string does not contain a valid address.
+ */
+public static Name
+fromAddress(String addr) throws UnknownHostException {
+	byte [] array = Address.toByteArray(addr, Address.IPv4);
+	if (array == null)
+		array = Address.toByteArray(addr, Address.IPv6);
+	if (array == null)
+		throw new UnknownHostException("Invalid IP address");
+	return fromAddress(array);
+}
+
+}
diff --git a/src/org/xbill/DNS/SIG0.java b/src/org/xbill/DNS/SIG0.java
new file mode 100644
index 0000000..5a00e72
--- /dev/null
+++ b/src/org/xbill/DNS/SIG0.java
@@ -0,0 +1,79 @@
+// Copyright (c) 2001-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.security.PrivateKey;
+import java.util.Date;
+
+/**
+ * Creates SIG(0) transaction signatures.
+ *
+ * @author Pasi Eronen
+ * @author Brian Wellington
+ */
+
+public class SIG0 {
+
+/**
+ * The default validity period for outgoing SIG(0) signed messages.
+ * Can be overriden by the sig0validity option.
+ */
+private static final short VALIDITY = 300;
+    
+private
+SIG0() { }
+
+/**
+ * Sign a message with SIG(0). The DNS key and private key must refer to the
+ * same underlying cryptographic key.
+ * @param message The message to be signed
+ * @param key The DNSKEY record to use as part of signing
+ * @param privkey The PrivateKey to use when signing
+ * @param previous If this message is a response, the SIG(0) from the query
+ */
+public static void
+signMessage(Message message, KEYRecord key, PrivateKey privkey,
+	    SIGRecord previous) throws DNSSEC.DNSSECException
+{
+	
+	int validity = Options.intValue("sig0validity");
+	if (validity < 0)
+		validity = VALIDITY;
+
+	long now = System.currentTimeMillis();
+	Date timeSigned = new Date(now);
+	Date timeExpires = new Date(now + validity * 1000);
+
+	SIGRecord sig =  DNSSEC.signMessage(message, previous, key, privkey,
+					    timeSigned, timeExpires);
+	
+	message.addRecord(sig, Section.ADDITIONAL);
+}
+
+/**
+ * Verify a message using SIG(0).
+ * @param message The message to be signed
+ * @param b An array containing the message in unparsed form.  This is
+ * necessary since SIG(0) signs the message in wire format, and we can't
+ * recreate the exact wire format (with the same name compression).
+ * @param key The KEY record to verify the signature with.
+ * @param previous If this message is a response, the SIG(0) from the query
+ */
+public static void
+verifyMessage(Message message, byte [] b, KEYRecord key, SIGRecord previous)
+	throws DNSSEC.DNSSECException
+{
+	SIGRecord sig = null;
+	Record [] additional = message.getSectionArray(Section.ADDITIONAL);
+	for (int i = 0; i < additional.length; i++) {
+		if (additional[i].getType() != Type.SIG)
+			continue;
+		if (((SIGRecord) additional[i]).getTypeCovered() != 0)
+			continue;
+		sig = (SIGRecord) additional[i];
+		break;
+	}
+	DNSSEC.verifyMessage(message, b, sig, previous, key);
+}
+
+}
diff --git a/src/org/xbill/DNS/SIGBase.java b/src/org/xbill/DNS/SIGBase.java
new file mode 100644
index 0000000..6e5f12d
--- /dev/null
+++ b/src/org/xbill/DNS/SIGBase.java
@@ -0,0 +1,193 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * The base class for SIG/RRSIG records, which have identical formats 
+ *
+ * @author Brian Wellington
+ */
+
+abstract class SIGBase extends Record {
+
+private static final long serialVersionUID = -3738444391533812369L;
+
+protected int covered;
+protected int alg, labels;
+protected long origttl;
+protected Date expire, timeSigned;
+protected int footprint;
+protected Name signer;
+protected byte [] signature;
+
+protected
+SIGBase() {}
+
+public
+SIGBase(Name name, int type, int dclass, long ttl, int covered, int alg,
+	long origttl, Date expire, Date timeSigned, int footprint, Name signer,
+	byte [] signature)
+{
+	super(name, type, dclass, ttl);
+	Type.check(covered);
+	TTL.check(origttl);
+	this.covered = covered;
+	this.alg = checkU8("alg", alg);
+	this.labels = name.labels() - 1;
+	if (name.isWild())
+		this.labels--;
+	this.origttl = origttl;
+	this.expire = expire;
+	this.timeSigned = timeSigned;
+	this.footprint = checkU16("footprint", footprint);
+	this.signer = checkName("signer", signer);
+	this.signature = signature;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	covered = in.readU16();
+	alg = in.readU8();
+	labels = in.readU8();
+	origttl = in.readU32();
+	expire = new Date(1000 * in.readU32());
+	timeSigned = new Date(1000 * in.readU32());
+	footprint = in.readU16();
+	signer = new Name(in);
+	signature = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String typeString = st.getString();
+	covered = Type.value(typeString);
+	if (covered < 0)
+		throw st.exception("Invalid type: " + typeString);
+	String algString = st.getString();
+	alg = DNSSEC.Algorithm.value(algString);
+	if (alg < 0)
+		throw st.exception("Invalid algorithm: " + algString);
+	labels = st.getUInt8();
+	origttl = st.getTTL();
+	expire = FormattedTime.parse(st.getString());
+	timeSigned = FormattedTime.parse(st.getString());
+	footprint = st.getUInt16();
+	signer = st.getName(origin);
+	signature = st.getBase64();
+}
+
+/** Converts the RRSIG/SIG Record to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append (Type.string(covered));
+	sb.append (" ");
+	sb.append (alg);
+	sb.append (" ");
+	sb.append (labels);
+	sb.append (" ");
+	sb.append (origttl);
+	sb.append (" ");
+	if (Options.check("multiline"))
+		sb.append ("(\n\t");
+	sb.append (FormattedTime.format(expire));
+	sb.append (" ");
+	sb.append (FormattedTime.format(timeSigned));
+	sb.append (" ");
+	sb.append (footprint);
+	sb.append (" ");
+	sb.append (signer);
+	if (Options.check("multiline")) {
+		sb.append("\n");
+		sb.append(base64.formatString(signature, 64, "\t",
+					      true));
+	} else {
+		sb.append (" ");
+		sb.append(base64.toString(signature));
+	}
+	return sb.toString();
+}
+
+/** Returns the RRset type covered by this signature */
+public int
+getTypeCovered() {
+	return covered;
+}
+
+/**
+ * Returns the cryptographic algorithm of the key that generated the signature
+ */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ * Returns the number of labels in the signed domain name.  This may be
+ * different than the record's domain name if the record is a wildcard
+ * record.
+ */
+public int
+getLabels() {
+	return labels;
+}
+
+/** Returns the original TTL of the RRset */
+public long
+getOrigTTL() {
+	return origttl;
+}
+
+/** Returns the time at which the signature expires */
+public Date
+getExpire() {
+	return expire;
+}
+
+/** Returns the time at which this signature was generated */
+public Date
+getTimeSigned() {
+	return timeSigned;
+}
+
+/** Returns The footprint/key id of the signing key.  */
+public int
+getFootprint() {
+	return footprint;
+}
+
+/** Returns the owner of the signing key */
+public Name
+getSigner() {
+	return signer;
+}
+
+/** Returns the binary data representing the signature */
+public byte []
+getSignature() {
+	return signature;
+}
+
+void
+setSignature(byte [] signature) {
+	this.signature = signature;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(covered);
+	out.writeU8(alg);
+	out.writeU8(labels);
+	out.writeU32(origttl);
+	out.writeU32(expire.getTime() / 1000);
+	out.writeU32(timeSigned.getTime() / 1000);
+	out.writeU16(footprint);
+	signer.toWire(out, null, canonical);
+	out.writeByteArray(signature);
+}
+
+}
diff --git a/src/org/xbill/DNS/SIGRecord.java b/src/org/xbill/DNS/SIGRecord.java
new file mode 100644
index 0000000..8b6f58d
--- /dev/null
+++ b/src/org/xbill/DNS/SIGRecord.java
@@ -0,0 +1,50 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * Signature - A SIG provides the digital signature of an RRset, so that
+ * the data can be authenticated by a DNSSEC-capable resolver.  The
+ * signature is usually generated by a key contained in a KEYRecord
+ * @see RRset
+ * @see DNSSEC
+ * @see KEYRecord
+ *
+ * @author Brian Wellington
+ */
+
+public class SIGRecord extends SIGBase {
+
+private static final long serialVersionUID = 4963556060953589058L;
+
+SIGRecord() {}
+
+Record
+getObject() {
+	return new SIGRecord();
+}
+
+/**
+ * Creates an SIG Record from the given data
+ * @param covered The RRset type covered by this signature
+ * @param alg The cryptographic algorithm of the key that generated the
+ * signature
+ * @param origttl The original TTL of the RRset
+ * @param expire The time at which the signature expires
+ * @param timeSigned The time at which this signature was generated
+ * @param footprint The footprint/key id of the signing key.
+ * @param signer The owner of the signing key
+ * @param signature Binary data representing the signature
+ */
+public
+SIGRecord(Name name, int dclass, long ttl, int covered, int alg, long origttl,
+	  Date expire, Date timeSigned, int footprint, Name signer,
+	  byte [] signature)
+{
+	super(name, Type.SIG, dclass, ttl, covered, alg, origttl, expire,
+	      timeSigned, footprint, signer, signature);
+}
+
+}
diff --git a/src/org/xbill/DNS/SOARecord.java b/src/org/xbill/DNS/SOARecord.java
new file mode 100644
index 0000000..7f27077
--- /dev/null
+++ b/src/org/xbill/DNS/SOARecord.java
@@ -0,0 +1,162 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Start of Authority - describes properties of a zone.
+ *
+ * @author Brian Wellington
+ */
+
+public class SOARecord extends Record {
+
+private static final long serialVersionUID = 1049740098229303931L;
+
+private Name host, admin;
+private long serial, refresh, retry, expire, minimum;
+
+SOARecord() {}
+
+Record
+getObject() {
+	return new SOARecord();
+}
+
+/**
+ * Creates an SOA Record from the given data
+ * @param host The primary name server for the zone
+ * @param admin The zone administrator's address
+ * @param serial The zone's serial number
+ * @param refresh The amount of time until a secondary checks for a new serial
+ * number
+ * @param retry The amount of time between a secondary's checks for a new
+ * serial number
+ * @param expire The amount of time until a secondary expires a zone
+ * @param minimum The minimum TTL for records in the zone
+*/
+public
+SOARecord(Name name, int dclass, long ttl, Name host, Name admin,
+	  long serial, long refresh, long retry, long expire, long minimum)
+{
+	super(name, Type.SOA, dclass, ttl);
+	this.host = checkName("host", host);
+	this.admin = checkName("admin", admin);
+	this.serial = checkU32("serial", serial);
+	this.refresh = checkU32("refresh", refresh);
+	this.retry = checkU32("retry", retry);
+	this.expire = checkU32("expire", expire);
+	this.minimum = checkU32("minimum", minimum);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	host = new Name(in);
+	admin = new Name(in);
+	serial = in.readU32();
+	refresh = in.readU32();
+	retry = in.readU32();
+	expire = in.readU32();
+	minimum = in.readU32();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	host = st.getName(origin);
+	admin = st.getName(origin);
+	serial = st.getUInt32();
+	refresh = st.getTTLLike();
+	retry = st.getTTLLike();
+	expire = st.getTTLLike();
+	minimum = st.getTTLLike();
+}
+
+/** Convert to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(host);
+	sb.append(" ");
+	sb.append(admin);
+	if (Options.check("multiline")) {
+		sb.append(" (\n\t\t\t\t\t");
+		sb.append(serial);
+		sb.append("\t; serial\n\t\t\t\t\t");
+		sb.append(refresh);
+		sb.append("\t; refresh\n\t\t\t\t\t");
+		sb.append(retry);
+		sb.append("\t; retry\n\t\t\t\t\t");
+		sb.append(expire);
+		sb.append("\t; expire\n\t\t\t\t\t");
+		sb.append(minimum);
+		sb.append(" )\t; minimum");
+	} else {
+		sb.append(" ");
+		sb.append(serial);
+		sb.append(" ");
+		sb.append(refresh);
+		sb.append(" ");
+		sb.append(retry);
+		sb.append(" ");
+		sb.append(expire);
+		sb.append(" ");
+		sb.append(minimum);
+	}
+	return sb.toString();
+}
+
+/** Returns the primary name server */
+public Name
+getHost() {  
+	return host;
+}       
+
+/** Returns the zone administrator's address */
+public Name
+getAdmin() {  
+	return admin;
+}       
+
+/** Returns the zone's serial number */
+public long
+getSerial() {  
+	return serial;
+}       
+
+/** Returns the zone refresh interval */
+public long
+getRefresh() {  
+	return refresh;
+}       
+
+/** Returns the zone retry interval */
+public long
+getRetry() {  
+	return retry;
+}       
+
+/** Returns the time until a secondary expires a zone */
+public long
+getExpire() {  
+	return expire;
+}       
+
+/** Returns the minimum TTL for records in the zone */
+public long
+getMinimum() {  
+	return minimum;
+}       
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	host.toWire(out, c, canonical);
+	admin.toWire(out, c, canonical);
+	out.writeU32(serial);
+	out.writeU32(refresh);
+	out.writeU32(retry);
+	out.writeU32(expire);
+	out.writeU32(minimum);
+}
+
+}
diff --git a/src/org/xbill/DNS/SPFRecord.java b/src/org/xbill/DNS/SPFRecord.java
new file mode 100644
index 0000000..a286220
--- /dev/null
+++ b/src/org/xbill/DNS/SPFRecord.java
@@ -0,0 +1,44 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * Sender Policy Framework (RFC 4408, experimental)
+ *
+ * @author Brian Wellington
+ */
+
+public class SPFRecord extends TXTBase {
+
+private static final long serialVersionUID = -2100754352801658722L;
+
+SPFRecord() {}
+
+Record
+getObject() {
+	return new SPFRecord();
+}
+
+/**
+ * Creates a SPF Record from the given data
+ * @param strings The text strings
+ * @throws IllegalArgumentException One of the strings has invalid escapes
+ */
+public
+SPFRecord(Name name, int dclass, long ttl, List strings) {
+	super(name, Type.SPF, dclass, ttl, strings);
+}
+
+/**
+ * Creates a SPF Record from the given data
+ * @param string One text string
+ * @throws IllegalArgumentException The string has invalid escapes
+ */
+public
+SPFRecord(Name name, int dclass, long ttl, String string) {
+	super(name, Type.SPF, dclass, ttl, string);
+}
+
+}
diff --git a/src/org/xbill/DNS/SRVRecord.java b/src/org/xbill/DNS/SRVRecord.java
new file mode 100644
index 0000000..c0635fb
--- /dev/null
+++ b/src/org/xbill/DNS/SRVRecord.java
@@ -0,0 +1,114 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Server Selection Record  - finds hosts running services in a domain.  An
+ * SRV record will normally be named _&lt;service&gt;._&lt;protocol&gt;.domain
+ * - examples would be _sips._tcp.example.org (for the secure SIP protocol) and
+ * _http._tcp.example.com (if HTTP used SRV records)
+ *
+ * @author Brian Wellington
+ */
+
+public class SRVRecord extends Record {
+
+private static final long serialVersionUID = -3886460132387522052L;
+
+private int priority, weight, port;
+private Name target;
+
+SRVRecord() {}
+
+Record
+getObject() {
+	return new SRVRecord();
+}
+
+/**
+ * Creates an SRV Record from the given data
+ * @param priority The priority of this SRV.  Records with lower priority
+ * are preferred.
+ * @param weight The weight, used to select between records at the same
+ * priority.
+ * @param port The TCP/UDP port that the service uses
+ * @param target The host running the service
+ */
+public
+SRVRecord(Name name, int dclass, long ttl, int priority,
+	  int weight, int port, Name target)
+{
+	super(name, Type.SRV, dclass, ttl);
+	this.priority = checkU16("priority", priority);
+	this.weight = checkU16("weight", weight);
+	this.port = checkU16("port", port);
+	this.target = checkName("target", target);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	priority = in.readU16();
+	weight = in.readU16();
+	port = in.readU16();
+	target = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	priority = st.getUInt16();
+	weight = st.getUInt16();
+	port = st.getUInt16();
+	target = st.getName(origin);
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(priority + " ");
+	sb.append(weight + " ");
+	sb.append(port + " ");
+	sb.append(target);
+	return sb.toString();
+}
+
+/** Returns the priority */
+public int
+getPriority() {
+	return priority;
+}
+
+/** Returns the weight */
+public int
+getWeight() {
+	return weight;
+}
+
+/** Returns the port that the service runs on */
+public int
+getPort() {
+	return port;
+}
+
+/** Returns the host running that the service */
+public Name
+getTarget() {
+	return target;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(priority);
+	out.writeU16(weight);
+	out.writeU16(port);
+	target.toWire(out, null, canonical);
+}
+
+public Name
+getAdditionalName() {
+	return target;
+}
+
+}
diff --git a/src/org/xbill/DNS/SSHFPRecord.java b/src/org/xbill/DNS/SSHFPRecord.java
new file mode 100644
index 0000000..079741e
--- /dev/null
+++ b/src/org/xbill/DNS/SSHFPRecord.java
@@ -0,0 +1,108 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * SSH Fingerprint - stores the fingerprint of an SSH host key.
+ *
+ * @author Brian Wellington
+ */
+
+public class SSHFPRecord extends Record {
+
+private static final long serialVersionUID = -8104701402654687025L;
+
+public static class Algorithm {
+	private Algorithm() {}
+
+	public static final int RSA = 1;
+	public static final int DSS = 2;
+}
+
+public static class Digest {
+	private Digest() {}
+
+	public static final int SHA1 = 1;
+}
+
+private int alg;
+private int digestType;
+private byte [] fingerprint;
+
+SSHFPRecord() {} 
+
+Record
+getObject() {
+	return new SSHFPRecord();
+}
+
+/**
+ * Creates an SSHFP Record from the given data.
+ * @param alg The public key's algorithm.
+ * @param digestType The public key's digest type.
+ * @param fingerprint The public key's fingerprint.
+ */
+public
+SSHFPRecord(Name name, int dclass, long ttl, int alg, int digestType,
+	    byte [] fingerprint)
+{
+	super(name, Type.SSHFP, dclass, ttl);
+	this.alg = checkU8("alg", alg);
+	this.digestType = checkU8("digestType", digestType);
+	this.fingerprint = fingerprint;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	alg = in.readU8();
+	digestType = in.readU8();
+	fingerprint = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	alg = st.getUInt8();
+	digestType = st.getUInt8();
+	fingerprint = st.getHex(true);
+}
+
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(alg);
+	sb.append(" ");
+	sb.append(digestType);
+	sb.append(" ");
+	sb.append(base16.toString(fingerprint));
+	return sb.toString();
+}
+
+/** Returns the public key's algorithm. */
+public int
+getAlgorithm() {
+	return alg;
+}
+
+/** Returns the public key's digest type. */
+public int
+getDigestType() {
+	return digestType;
+}
+
+/** Returns the fingerprint */
+public byte []
+getFingerPrint() {
+	return fingerprint;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(alg);
+	out.writeU8(digestType);
+	out.writeByteArray(fingerprint);
+}
+
+}
diff --git a/src/org/xbill/DNS/Section.java b/src/org/xbill/DNS/Section.java
new file mode 100644
index 0000000..e0c8caa
--- /dev/null
+++ b/src/org/xbill/DNS/Section.java
@@ -0,0 +1,92 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Constants and functions relating to DNS message sections
+ *
+ * @author Brian Wellington
+ */
+
+public final class Section {
+
+/** The question (first) section */
+public static final int QUESTION	= 0;
+
+/** The answer (second) section */
+public static final int ANSWER		= 1;
+
+/** The authority (third) section */
+public static final int AUTHORITY	= 2;
+
+/** The additional (fourth) section */
+public static final int ADDITIONAL	= 3;
+
+/* Aliases for dynamic update */
+/** The zone (first) section of a dynamic update message */
+public static final int ZONE		= 0;
+
+/** The prerequisite (second) section of a dynamic update message */
+public static final int PREREQ		= 1;
+
+/** The update (third) section of a dynamic update message */
+public static final int UPDATE		= 2;
+
+private static Mnemonic sections = new Mnemonic("Message Section",
+						Mnemonic.CASE_LOWER);
+private static String [] longSections = new String[4];
+private static String [] updateSections = new String[4];
+
+static {
+	sections.setMaximum(3);
+	sections.setNumericAllowed(true);
+
+	sections.add(QUESTION, "qd");
+	sections.add(ANSWER, "an");
+	sections.add(AUTHORITY, "au");
+	sections.add(ADDITIONAL, "ad");
+
+	longSections[QUESTION]		= "QUESTIONS";
+	longSections[ANSWER]		= "ANSWERS";
+	longSections[AUTHORITY]		= "AUTHORITY RECORDS";
+	longSections[ADDITIONAL]	= "ADDITIONAL RECORDS";
+
+	updateSections[ZONE]		= "ZONE";
+	updateSections[PREREQ]		= "PREREQUISITES";
+	updateSections[UPDATE]		= "UPDATE RECORDS";
+	updateSections[ADDITIONAL]	= "ADDITIONAL RECORDS";
+}
+
+private
+Section() {}
+
+/** Converts a numeric Section into an abbreviation String */
+public static String
+string(int i) {
+	return sections.getText(i);
+}
+
+/** Converts a numeric Section into a full description String */
+public static String
+longString(int i) {
+	sections.check(i);
+	return longSections[i];
+}
+
+/**
+ * Converts a numeric Section into a full description String for an update
+ * Message.
+ */
+public static String
+updString(int i) {
+	sections.check(i);
+	return updateSections[i];
+}
+
+/** Converts a String representation of a Section into its numeric value */
+public static int
+value(String s) {
+	return sections.getValue(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/Serial.java b/src/org/xbill/DNS/Serial.java
new file mode 100644
index 0000000..3a146c6
--- /dev/null
+++ b/src/org/xbill/DNS/Serial.java
@@ -0,0 +1,61 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Helper functions for doing serial arithmetic.  These should be used when
+ * setting/checking SOA serial numbers.  SOA serial number arithmetic is
+ * defined in RFC 1982.
+ *
+ * @author Brian Wellington
+ */
+
+public final class Serial {
+
+private static final long MAX32 = 0xFFFFFFFFL;
+
+private
+Serial() {
+}
+
+/**
+ * Compares two numbers using serial arithmetic.  The numbers are assumed
+ * to be 32 bit unsigned integers stored in longs.
+ * @param serial1 The first integer
+ * @param serial2 The second integer
+ * @return 0 if the 2 numbers are equal, a positive number if serial1 is greater
+ * than serial2, and a negative number if serial2 is greater than serial1.
+ * @throws IllegalArgumentException serial1 or serial2 is out of range
+ */
+public static int
+compare(long serial1, long serial2) {
+	if (serial1 < 0 || serial1 > MAX32)
+		throw new IllegalArgumentException(serial1 + " out of range");
+	if (serial2 < 0 || serial2 > MAX32)
+		throw new IllegalArgumentException(serial2 + " out of range");
+	long diff = serial1 - serial2;
+	if (diff >= MAX32)
+		diff -= (MAX32 + 1);
+	else if (diff < -MAX32)
+		diff += (MAX32 + 1);
+	return (int)diff;
+}
+
+/**
+ * Increments a serial number.  The number is assumed to be a 32 bit unsigned
+ * integer stored in a long.  This basically adds 1 and resets the value to
+ * 0 if it is 2^32.
+ * @param serial The serial number
+ * @return The incremented serial number
+ * @throws IllegalArgumentException serial is out of range
+ */
+public static long
+increment(long serial) {
+	if (serial < 0 || serial > MAX32)
+		throw new IllegalArgumentException(serial + " out of range");
+	if (serial == MAX32)
+		return 0;
+	return serial + 1;
+}
+
+}
diff --git a/src/org/xbill/DNS/SetResponse.java b/src/org/xbill/DNS/SetResponse.java
new file mode 100644
index 0000000..05d9f32
--- /dev/null
+++ b/src/org/xbill/DNS/SetResponse.java
@@ -0,0 +1,202 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * The Response from a query to Cache.lookupRecords() or Zone.findRecords()
+ * @see Cache
+ * @see Zone
+ *
+ * @author Brian Wellington
+ */
+
+public class SetResponse {
+
+/**
+ * The Cache contains no information about the requested name/type
+ */
+static final int UNKNOWN	= 0;
+
+/**
+ * The Zone does not contain the requested name, or the Cache has
+ * determined that the name does not exist.
+ */
+static final int NXDOMAIN	= 1;
+
+/**
+ * The Zone contains the name, but no data of the requested type,
+ * or the Cache has determined that the name exists and has no data
+ * of the requested type.
+ */
+static final int NXRRSET	= 2;
+
+/**
+ * A delegation enclosing the requested name was found.
+ */
+static final int DELEGATION	= 3;
+
+/**
+ * The Cache/Zone found a CNAME when looking for the name.
+ * @see CNAMERecord
+ */
+static final int CNAME		= 4;
+
+/**
+ * The Cache/Zone found a DNAME when looking for the name.
+ * @see DNAMERecord
+ */
+static final int DNAME		= 5;
+
+/**
+ * The Cache/Zone has successfully answered the question for the
+ * requested name/type/class.
+ */
+static final int SUCCESSFUL	= 6;
+
+private static final SetResponse unknown = new SetResponse(UNKNOWN);
+private static final SetResponse nxdomain = new SetResponse(NXDOMAIN);
+private static final SetResponse nxrrset = new SetResponse(NXRRSET);
+
+private int type;
+private Object data;
+
+private
+SetResponse() {}
+
+SetResponse(int type, RRset rrset) {
+	if (type < 0 || type > 6)
+		throw new IllegalArgumentException("invalid type");
+	this.type = type;
+	this.data = rrset;
+}
+
+SetResponse(int type) {
+	if (type < 0 || type > 6)
+		throw new IllegalArgumentException("invalid type");
+	this.type = type;
+	this.data = null;
+}
+
+static SetResponse
+ofType(int type) {
+	switch (type) {
+		case UNKNOWN:
+			return unknown;
+		case NXDOMAIN:
+			return nxdomain;
+		case NXRRSET:
+			return nxrrset;
+		case DELEGATION:
+		case CNAME:
+		case DNAME:
+		case SUCCESSFUL:
+			SetResponse sr = new SetResponse();
+			sr.type = type;
+			sr.data = null;
+			return sr;
+		default:
+			throw new IllegalArgumentException("invalid type");
+	}
+}
+
+void
+addRRset(RRset rrset) {
+	if (data == null)
+		data = new ArrayList();
+	List l = (List) data;
+	l.add(rrset);
+}
+
+/** Is the answer to the query unknown? */
+public boolean
+isUnknown() {
+	return (type == UNKNOWN);
+}
+
+/** Is the answer to the query that the name does not exist? */
+public boolean
+isNXDOMAIN() {
+	return (type == NXDOMAIN);
+}
+
+/** Is the answer to the query that the name exists, but the type does not? */
+public boolean
+isNXRRSET() {
+	return (type == NXRRSET);
+}
+
+/** Is the result of the lookup that the name is below a delegation? */
+public boolean
+isDelegation() {
+	return (type == DELEGATION);
+}
+
+/** Is the result of the lookup a CNAME? */
+public boolean
+isCNAME() {
+	return (type == CNAME);
+}
+
+/** Is the result of the lookup a DNAME? */
+public boolean
+isDNAME() {
+	return (type == DNAME);
+}
+
+/** Was the query successful? */
+public boolean
+isSuccessful() {
+	return (type == SUCCESSFUL);
+}
+
+/** If the query was successful, return the answers */
+public RRset []
+answers() {
+	if (type != SUCCESSFUL)
+		return null;
+	List l = (List) data;
+	return (RRset []) l.toArray(new RRset[l.size()]);
+}
+
+/**
+ * If the query encountered a CNAME, return it.
+ */
+public CNAMERecord
+getCNAME() {
+	return (CNAMERecord)((RRset)data).first();
+}
+
+/**
+ * If the query encountered a DNAME, return it.
+ */
+public DNAMERecord
+getDNAME() {
+	return (DNAMERecord)((RRset)data).first();
+}
+
+/**
+ * If the query hit a delegation point, return the NS set.
+ */
+public RRset
+getNS() {
+	return (RRset)data;
+}
+
+/** Prints the value of the SetResponse */
+public String
+toString() {
+	switch (type) {
+		case UNKNOWN:		return "unknown";
+		case NXDOMAIN:		return "NXDOMAIN";
+		case NXRRSET:		return "NXRRSET";
+		case DELEGATION:	return "delegation: " + data;
+		case CNAME:		return "CNAME: " + data;
+		case DNAME:		return "DNAME: " + data;
+		case SUCCESSFUL:	return "successful";
+		default:		throw new IllegalStateException();
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/SimpleResolver.java b/src/org/xbill/DNS/SimpleResolver.java
new file mode 100644
index 0000000..7436133
--- /dev/null
+++ b/src/org/xbill/DNS/SimpleResolver.java
@@ -0,0 +1,351 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+import java.io.*;
+import java.net.*;
+
+/**
+ * An implementation of Resolver that sends one query to one server.
+ * SimpleResolver handles TCP retries, transaction security (TSIG), and
+ * EDNS 0.
+ * @see Resolver
+ * @see TSIG
+ * @see OPTRecord
+ *
+ * @author Brian Wellington
+ */
+
+
+public class SimpleResolver implements Resolver {
+
+/** The default port to send queries to */
+public static final int DEFAULT_PORT = 53;
+
+/** The default EDNS payload size */
+public static final int DEFAULT_EDNS_PAYLOADSIZE = 1280;
+
+private InetSocketAddress address;
+private InetSocketAddress localAddress;
+private boolean useTCP, ignoreTruncation;
+private OPTRecord queryOPT;
+private TSIG tsig;
+private long timeoutValue = 10 * 1000;
+
+private static final short DEFAULT_UDPSIZE = 512;
+
+private static String defaultResolver = "localhost";
+private static int uniqueID = 0;
+
+/**
+ * Creates a SimpleResolver that will query the specified host 
+ * @exception UnknownHostException Failure occurred while finding the host
+ */
+public
+SimpleResolver(String hostname) throws UnknownHostException {
+	if (hostname == null) {
+		hostname = ResolverConfig.getCurrentConfig().server();
+		if (hostname == null)
+			hostname = defaultResolver;
+	}
+	InetAddress addr;
+	if (hostname.equals("0"))
+		addr = InetAddress.getLocalHost();
+	else
+		addr = InetAddress.getByName(hostname);
+	address = new InetSocketAddress(addr, DEFAULT_PORT);
+}
+
+/**
+ * Creates a SimpleResolver.  The host to query is either found by using
+ * ResolverConfig, or the default host is used.
+ * @see ResolverConfig
+ * @exception UnknownHostException Failure occurred while finding the host
+ */
+public
+SimpleResolver() throws UnknownHostException {
+	this(null);
+}
+
+/**
+ * Gets the destination address associated with this SimpleResolver.
+ * Messages sent using this SimpleResolver will be sent to this address.
+ * @return The destination address associated with this SimpleResolver.
+ */
+InetSocketAddress
+getAddress() {
+	return address;
+}
+
+/** Sets the default host (initially localhost) to query */
+public static void
+setDefaultResolver(String hostname) {
+	defaultResolver = hostname;
+}
+
+public void
+setPort(int port) {
+	address = new InetSocketAddress(address.getAddress(), port);
+}
+
+/**
+ * Sets the address of the server to communicate with.
+ * @param addr The address of the DNS server
+ */
+public void
+setAddress(InetSocketAddress addr) {
+	address = addr;
+}
+
+/**
+ * Sets the address of the server to communicate with (on the default
+ * DNS port)
+ * @param addr The address of the DNS server
+ */
+public void
+setAddress(InetAddress addr) {
+	address = new InetSocketAddress(addr, address.getPort());
+}
+
+/**
+ * Sets the local address to bind to when sending messages.
+ * @param addr The local address to send messages from.
+ */
+public void
+setLocalAddress(InetSocketAddress addr) {
+	localAddress = addr;
+}
+
+/**
+ * Sets the local address to bind to when sending messages.  A random port
+ * will be used.
+ * @param addr The local address to send messages from.
+ */
+public void
+setLocalAddress(InetAddress addr) {
+	localAddress = new InetSocketAddress(addr, 0);
+}
+
+public void
+setTCP(boolean flag) {
+	this.useTCP = flag;
+}
+
+public void
+setIgnoreTruncation(boolean flag) {
+	this.ignoreTruncation = flag;
+}
+
+public void
+setEDNS(int level, int payloadSize, int flags, List options) {
+	if (level != 0 && level != -1)
+		throw new IllegalArgumentException("invalid EDNS level - " +
+						   "must be 0 or -1");
+	if (payloadSize == 0)
+		payloadSize = DEFAULT_EDNS_PAYLOADSIZE;
+	queryOPT = new OPTRecord(payloadSize, 0, level, flags, options);
+}
+
+public void
+setEDNS(int level) {
+	setEDNS(level, 0, 0, null);
+}
+
+public void
+setTSIGKey(TSIG key) {
+	tsig = key;
+}
+
+TSIG
+getTSIGKey() {
+	return tsig;
+}
+
+public void
+setTimeout(int secs, int msecs) {
+	timeoutValue = (long)secs * 1000 + msecs;
+}
+
+public void
+setTimeout(int secs) {
+	setTimeout(secs, 0);
+}
+
+long
+getTimeout() {
+	return timeoutValue;
+}
+
+private Message
+parseMessage(byte [] b) throws WireParseException {
+	try {
+		return (new Message(b));
+	}
+	catch (IOException e) {
+		if (Options.check("verbose"))
+			e.printStackTrace();
+		if (!(e instanceof WireParseException))
+			e = new WireParseException("Error parsing message");
+		throw (WireParseException) e;
+	}
+}
+
+private void
+verifyTSIG(Message query, Message response, byte [] b, TSIG tsig) {
+	if (tsig == null)
+		return;
+	int error = tsig.verify(response, b, query.getTSIG());
+	if (Options.check("verbose"))
+		System.err.println("TSIG verify: " + Rcode.TSIGstring(error));
+}
+
+private void
+applyEDNS(Message query) {
+	if (queryOPT == null || query.getOPT() != null)
+		return;
+	query.addRecord(queryOPT, Section.ADDITIONAL);
+}
+
+private int
+maxUDPSize(Message query) {
+	OPTRecord opt = query.getOPT();
+	if (opt == null)
+		return DEFAULT_UDPSIZE;
+	else
+		return opt.getPayloadSize();
+}
+
+/**
+ * Sends a message to a single server and waits for a response.  No checking
+ * is done to ensure that the response is associated with the query.
+ * @param query The query to send.
+ * @return The response.
+ * @throws IOException An error occurred while sending or receiving.
+ */
+public Message
+send(Message query) throws IOException {
+	if (Options.check("verbose"))
+		System.err.println("Sending to " +
+				   address.getAddress().getHostAddress() +
+				   ":" + address.getPort());
+
+	if (query.getHeader().getOpcode() == Opcode.QUERY) {
+		Record question = query.getQuestion();
+		if (question != null && question.getType() == Type.AXFR)
+			return sendAXFR(query);
+	}
+
+	query = (Message) query.clone();
+	applyEDNS(query);
+	if (tsig != null)
+		tsig.apply(query, null);
+
+	byte [] out = query.toWire(Message.MAXLENGTH);
+	int udpSize = maxUDPSize(query);
+	boolean tcp = false;
+	long endTime = System.currentTimeMillis() + timeoutValue;
+	do {
+		byte [] in;
+
+		if (useTCP || out.length > udpSize)
+			tcp = true;
+		if (tcp)
+			in = TCPClient.sendrecv(localAddress, address, out,
+						endTime);
+		else
+			in = UDPClient.sendrecv(localAddress, address, out,
+						udpSize, endTime);
+
+		/*
+		 * Check that the response is long enough.
+		 */
+		if (in.length < Header.LENGTH) {
+			throw new WireParseException("invalid DNS header - " +
+						     "too short");
+		}
+		/*
+		 * Check that the response ID matches the query ID.  We want
+		 * to check this before actually parsing the message, so that
+		 * if there's a malformed response that's not ours, it
+		 * doesn't confuse us.
+		 */
+		int id = ((in[0] & 0xFF) << 8) + (in[1] & 0xFF);
+		int qid = query.getHeader().getID();
+		if (id != qid) {
+			String error = "invalid message id: expected " + qid +
+				       "; got id " + id;
+			if (tcp) {
+				throw new WireParseException(error);
+			} else {
+				if (Options.check("verbose")) {
+					System.err.println(error);
+				}
+				continue;
+			}
+		}
+		Message response = parseMessage(in);
+		verifyTSIG(query, response, in, tsig);
+		if (!tcp && !ignoreTruncation &&
+		    response.getHeader().getFlag(Flags.TC))
+		{
+			tcp = true;
+			continue;
+		}
+		return response;
+	} while (true);
+}
+
+/**
+ * Asynchronously sends a message to a single server, registering a listener
+ * to receive a callback on success or exception.  Multiple asynchronous
+ * lookups can be performed in parallel.  Since the callback may be invoked
+ * before the function returns, external synchronization is necessary.
+ * @param query The query to send
+ * @param listener The object containing the callbacks.
+ * @return An identifier, which is also a parameter in the callback
+ */
+public Object
+sendAsync(final Message query, final ResolverListener listener) {
+	final Object id;
+	synchronized (this) {
+		id = new Integer(uniqueID++);
+	}
+	Record question = query.getQuestion();
+	String qname;
+	if (question != null)
+		qname = question.getName().toString();
+	else
+		qname = "(none)";
+	String name = this.getClass() + ": " + qname;
+	Thread thread = new ResolveThread(this, query, id, listener);
+	thread.setName(name);
+	thread.setDaemon(true);
+	thread.start();
+	return id;
+}
+
+private Message
+sendAXFR(Message query) throws IOException {
+	Name qname = query.getQuestion().getName();
+	ZoneTransferIn xfrin = ZoneTransferIn.newAXFR(qname, address, tsig);
+	xfrin.setTimeout((int)(getTimeout() / 1000));
+	xfrin.setLocalAddress(localAddress);
+	try {
+		xfrin.run();
+	}
+	catch (ZoneTransferException e) {
+		throw new WireParseException(e.getMessage());
+	}
+	List records = xfrin.getAXFR();
+	Message response = new Message(query.getHeader().getID());
+	response.getHeader().setFlag(Flags.AA);
+	response.getHeader().setFlag(Flags.QR);
+	response.addRecord(query.getQuestion(), Section.QUESTION);
+	Iterator it = records.iterator();
+	while (it.hasNext())
+		response.addRecord((Record)it.next(), Section.ANSWER);
+	return response;
+}
+
+}
diff --git a/src/org/xbill/DNS/SingleCompressedNameBase.java b/src/org/xbill/DNS/SingleCompressedNameBase.java
new file mode 100644
index 0000000..790ca1f
--- /dev/null
+++ b/src/org/xbill/DNS/SingleCompressedNameBase.java
@@ -0,0 +1,31 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Implements common functionality for the many record types whose format
+ * is a single compressed name.
+ *
+ * @author Brian Wellington
+ */
+
+abstract class SingleCompressedNameBase extends SingleNameBase {
+
+private static final long serialVersionUID = -236435396815460677L;
+
+protected
+SingleCompressedNameBase() {}
+
+protected
+SingleCompressedNameBase(Name name, int type, int dclass, long ttl,
+			 Name singleName, String description)
+{
+        super(name, type, dclass, ttl, singleName, description);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	singleName.toWire(out, c, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/SingleNameBase.java b/src/org/xbill/DNS/SingleNameBase.java
new file mode 100644
index 0000000..6d6c041
--- /dev/null
+++ b/src/org/xbill/DNS/SingleNameBase.java
@@ -0,0 +1,61 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Implements common functionality for the many record types whose format
+ * is a single name.
+ *
+ * @author Brian Wellington
+ */
+
+abstract class SingleNameBase extends Record {
+
+private static final long serialVersionUID = -18595042501413L;
+
+protected Name singleName;
+
+protected
+SingleNameBase() {}
+
+protected
+SingleNameBase(Name name, int type, int dclass, long ttl) {
+	super(name, type, dclass, ttl);
+}
+
+protected
+SingleNameBase(Name name, int type, int dclass, long ttl, Name singleName,
+	    String description)
+{
+	super(name, type, dclass, ttl);
+	this.singleName = checkName(description, singleName);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	singleName = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	singleName = st.getName(origin);
+}
+
+String
+rrToString() {
+	return singleName.toString();
+}
+
+protected Name
+getSingleName() {
+	return singleName;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	singleName.toWire(out, null, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/TCPClient.java b/src/org/xbill/DNS/TCPClient.java
new file mode 100644
index 0000000..1f17d72
--- /dev/null
+++ b/src/org/xbill/DNS/TCPClient.java
@@ -0,0 +1,132 @@
+// Copyright (c) 2005 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import java.nio.*;
+import java.nio.channels.*;
+
+final class TCPClient extends Client {
+
+public
+TCPClient(long endTime) throws IOException {
+	super(SocketChannel.open(), endTime);
+}
+
+void
+bind(SocketAddress addr) throws IOException {
+	SocketChannel channel = (SocketChannel) key.channel();
+	channel.socket().bind(addr);
+}
+
+void
+connect(SocketAddress addr) throws IOException {
+	SocketChannel channel = (SocketChannel) key.channel();
+	if (channel.connect(addr))
+		return;
+	key.interestOps(SelectionKey.OP_CONNECT);
+	try {
+		while (!channel.finishConnect()) {
+			if (!key.isConnectable())
+				blockUntil(key, endTime);
+		}
+	}
+	finally {
+		if (key.isValid())
+			key.interestOps(0);
+	}
+}
+
+void
+send(byte [] data) throws IOException {
+	SocketChannel channel = (SocketChannel) key.channel();
+	verboseLog("TCP write", data);
+	byte [] lengthArray = new byte[2];
+	lengthArray[0] = (byte)(data.length >>> 8);
+	lengthArray[1] = (byte)(data.length & 0xFF);
+	ByteBuffer [] buffers = new ByteBuffer[2];
+	buffers[0] = ByteBuffer.wrap(lengthArray);
+	buffers[1] = ByteBuffer.wrap(data);
+	int nsent = 0;
+	key.interestOps(SelectionKey.OP_WRITE);
+	try {
+		while (nsent < data.length + 2) {
+			if (key.isWritable()) {
+				long n = channel.write(buffers);
+				if (n < 0)
+					throw new EOFException();
+				nsent += (int) n;
+				if (nsent < data.length + 2 &&
+				    System.currentTimeMillis() > endTime)
+					throw new SocketTimeoutException();
+			} else
+				blockUntil(key, endTime);
+		}
+	}
+	finally {
+		if (key.isValid())
+			key.interestOps(0);
+	}
+}
+
+private byte []
+_recv(int length) throws IOException {
+	SocketChannel channel = (SocketChannel) key.channel();
+	int nrecvd = 0;
+	byte [] data = new byte[length];
+	ByteBuffer buffer = ByteBuffer.wrap(data);
+	key.interestOps(SelectionKey.OP_READ);
+	try {
+		while (nrecvd < length) {
+			if (key.isReadable()) {
+				long n = channel.read(buffer);
+				if (n < 0)
+					throw new EOFException();
+				nrecvd += (int) n;
+				if (nrecvd < length &&
+				    System.currentTimeMillis() > endTime)
+					throw new SocketTimeoutException();
+			} else
+				blockUntil(key, endTime);
+		}
+	}
+	finally {
+		if (key.isValid())
+			key.interestOps(0);
+	}
+	return data;
+}
+
+byte []
+recv() throws IOException {
+	byte [] buf = _recv(2);
+	int length = ((buf[0] & 0xFF) << 8) + (buf[1] & 0xFF);
+	byte [] data = _recv(length);
+	verboseLog("TCP read", data);
+	return data;
+}
+
+static byte []
+sendrecv(SocketAddress local, SocketAddress remote, byte [] data, long endTime)
+throws IOException
+{
+	TCPClient client = new TCPClient(endTime);
+	try {
+		if (local != null)
+			client.bind(local);
+		client.connect(remote);
+		client.send(data);
+		return client.recv();
+	}
+	finally {
+		client.cleanup();
+	}
+}
+
+static byte []
+sendrecv(SocketAddress addr, byte [] data, long endTime) throws IOException {
+	return sendrecv(null, addr, data, endTime);
+}
+
+}
diff --git a/src/org/xbill/DNS/TKEYRecord.java b/src/org/xbill/DNS/TKEYRecord.java
new file mode 100644
index 0000000..4dcbb5c
--- /dev/null
+++ b/src/org/xbill/DNS/TKEYRecord.java
@@ -0,0 +1,225 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * Transaction Key - used to compute and/or securely transport a shared
+ * secret to be used with TSIG.
+ * @see TSIG
+ *
+ * @author Brian Wellington
+ */
+
+public class TKEYRecord extends Record {
+
+private static final long serialVersionUID = 8828458121926391756L;
+
+private Name alg;
+private Date timeInception;
+private Date timeExpire;
+private int mode, error;
+private byte [] key;
+private byte [] other;
+
+/** The key is assigned by the server (unimplemented) */
+public static final int SERVERASSIGNED		= 1;
+
+/** The key is computed using a Diffie-Hellman key exchange */
+public static final int DIFFIEHELLMAN		= 2;
+
+/** The key is computed using GSS_API (unimplemented) */
+public static final int GSSAPI			= 3;
+
+/** The key is assigned by the resolver (unimplemented) */
+public static final int RESOLVERASSIGNED	= 4;
+
+/** The key should be deleted */
+public static final int DELETE			= 5;
+
+TKEYRecord() {}
+
+Record
+getObject() {
+	return new TKEYRecord();
+}
+
+/**
+ * Creates a TKEY Record from the given data.
+ * @param alg The shared key's algorithm
+ * @param timeInception The beginning of the validity period of the shared
+ * secret or keying material
+ * @param timeExpire The end of the validity period of the shared
+ * secret or keying material
+ * @param mode The mode of key agreement
+ * @param error The extended error field.  Should be 0 in queries
+ * @param key The shared secret
+ * @param other The other data field.  Currently unused
+ * responses.
+ */
+public
+TKEYRecord(Name name, int dclass, long ttl, Name alg,
+	   Date timeInception, Date timeExpire, int mode, int error,
+	   byte [] key, byte other[])
+{
+	super(name, Type.TKEY, dclass, ttl);
+	this.alg = checkName("alg", alg);
+	this.timeInception = timeInception;
+	this.timeExpire = timeExpire;
+	this.mode = checkU16("mode", mode);
+	this.error = checkU16("error", error);
+	this.key = key;
+	this.other = other;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	alg = new Name(in);
+	timeInception = new Date(1000 * in.readU32());
+	timeExpire = new Date(1000 * in.readU32());
+	mode = in.readU16();
+	error = in.readU16();
+
+	int keylen = in.readU16();
+	if (keylen > 0)
+		key = in.readByteArray(keylen);
+	else
+		key = null;
+
+	int otherlen = in.readU16();
+	if (otherlen > 0)
+		other = in.readByteArray(otherlen);
+	else
+		other = null;
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	throw st.exception("no text format defined for TKEY");
+}
+
+protected String
+modeString() {
+	switch (mode) {
+		case SERVERASSIGNED:	return "SERVERASSIGNED";
+		case DIFFIEHELLMAN:	return "DIFFIEHELLMAN";
+		case GSSAPI:		return "GSSAPI";
+		case RESOLVERASSIGNED:	return "RESOLVERASSIGNED";
+		case DELETE:		return "DELETE";
+		default:		return Integer.toString(mode);
+	}
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(alg);
+	sb.append(" ");
+	if (Options.check("multiline"))
+		sb.append("(\n\t");
+	sb.append(FormattedTime.format(timeInception));
+	sb.append(" ");
+	sb.append(FormattedTime.format(timeExpire));
+	sb.append(" ");
+	sb.append(modeString());
+	sb.append(" ");
+	sb.append(Rcode.TSIGstring(error));
+	if (Options.check("multiline")) {
+		sb.append("\n");
+		if (key != null) {
+			sb.append(base64.formatString(key, 64, "\t", false));
+			sb.append("\n");
+		}
+		if (other != null)
+			sb.append(base64.formatString(other, 64, "\t", false));
+		sb.append(" )");
+	} else {
+		sb.append(" ");
+		if (key != null) {
+			sb.append(base64.toString(key));
+			sb.append(" ");
+		}
+		if (other != null)
+			sb.append(base64.toString(other));
+	}
+	return sb.toString();
+}
+
+/** Returns the shared key's algorithm */
+public Name
+getAlgorithm() {
+	return alg;
+}
+
+/**
+ * Returns the beginning of the validity period of the shared secret or
+ * keying material
+ */
+public Date
+getTimeInception() {
+	return timeInception;
+}
+
+/**
+ * Returns the end of the validity period of the shared secret or
+ * keying material
+ */
+public Date
+getTimeExpire() {
+	return timeExpire;
+}
+
+/** Returns the key agreement mode */
+public int
+getMode() {
+	return mode;
+}
+
+/** Returns the extended error */
+public int
+getError() {
+	return error;
+}
+
+/** Returns the shared secret or keying material */
+public byte []
+getKey() {
+	return key;
+}
+
+/** Returns the other data */
+public byte []
+getOther() {
+	return other;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	alg.toWire(out, null, canonical);
+
+	out.writeU32(timeInception.getTime() / 1000);
+	out.writeU32(timeExpire.getTime() / 1000);
+
+	out.writeU16(mode);
+	out.writeU16(error);
+
+	if (key != null) {
+		out.writeU16(key.length);
+		out.writeByteArray(key);
+	}
+	else
+		out.writeU16(0);
+
+	if (other != null) {
+		out.writeU16(other.length);
+		out.writeByteArray(other);
+	}
+	else
+		out.writeU16(0);
+}
+
+}
diff --git a/src/org/xbill/DNS/TLSARecord.java b/src/org/xbill/DNS/TLSARecord.java
new file mode 100644
index 0000000..48e2e80
--- /dev/null
+++ b/src/org/xbill/DNS/TLSARecord.java
@@ -0,0 +1,156 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * Transport Layer Security Authentication
+ *
+ * @author Brian Wellington
+ */
+
+public class TLSARecord extends Record {
+
+private static final long serialVersionUID = 356494267028580169L;
+
+public static class CertificateUsage {
+	private CertificateUsage() {}
+
+	public static final int CA_CONSTRAINT = 0;
+	public static final int SERVICE_CERTIFICATE_CONSTRAINT = 1;
+	public static final int TRUST_ANCHOR_ASSERTION = 2;
+	public static final int DOMAIN_ISSUED_CERTIFICATE = 3;
+}
+
+public static class Selector {
+	private Selector() {}
+
+	/**
+	 * Full certificate; the Certificate binary structure defined in
+	 * [RFC5280]
+	 */
+	public static final int FULL_CERTIFICATE = 0;
+
+	/**
+	 * SubjectPublicKeyInfo; DER-encoded binary structure defined in
+	 * [RFC5280]
+	 */
+	public static final int SUBJECT_PUBLIC_KEY_INFO = 1;
+}
+
+public static class MatchingType {
+	private MatchingType() {}
+
+	/** Exact match on selected content */
+	public static final int EXACT = 0;
+
+	/** SHA-256 hash of selected content [RFC6234] */
+	public static final int SHA256 = 1;
+
+	/** SHA-512 hash of selected content [RFC6234] */
+	public static final int SHA512 = 2;
+}
+
+private int certificateUsage;
+private int selector;
+private int matchingType;
+private byte [] certificateAssociationData;
+
+TLSARecord() {}
+
+Record
+getObject() {
+	return new TLSARecord();
+}
+
+/**
+ * Creates an TLSA Record from the given data
+ * @param certificateUsage The provided association that will be used to
+ * match the certificate presented in the TLS handshake. 
+ * @param selector The part of the TLS certificate presented by the server
+ * that will be matched against the association data. 
+ * @param matchingType How the certificate association is presented.
+ * @param certificateAssociationData The "certificate association data" to be
+ * matched.
+ */
+public
+TLSARecord(Name name, int dclass, long ttl, 
+	   int certificateUsage, int selector, int matchingType,
+	   byte [] certificateAssociationData)
+{
+	super(name, Type.TLSA, dclass, ttl);
+	this.certificateUsage = checkU8("certificateUsage", certificateUsage);
+	this.selector = checkU8("selector", selector);
+	this.matchingType = checkU8("matchingType", matchingType);
+	this.certificateAssociationData = checkByteArrayLength(
+						"certificateAssociationData",
+						certificateAssociationData,
+						0xFFFF);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	certificateUsage = in.readU8();
+	selector = in.readU8();
+	matchingType = in.readU8();
+	certificateAssociationData = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	certificateUsage = st.getUInt8();
+	selector = st.getUInt8();
+	matchingType = st.getUInt8();
+	certificateAssociationData = st.getHex();
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(certificateUsage);
+	sb.append(" ");
+	sb.append(selector);
+	sb.append(" ");
+	sb.append(matchingType);
+	sb.append(" ");
+	sb.append(base16.toString(certificateAssociationData));
+
+	return sb.toString();
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU8(certificateUsage);
+	out.writeU8(selector);
+	out.writeU8(matchingType);
+	out.writeByteArray(certificateAssociationData);
+}
+
+/** Returns the certificate usage of the TLSA record */
+public int
+getCertificateUsage() {
+	return certificateUsage;
+}
+
+/** Returns the selector of the TLSA record */
+public int
+getSelector() {
+	return selector;
+}
+
+/** Returns the matching type of the TLSA record */
+public int
+getMatchingType() {
+	return matchingType;
+}
+
+/** Returns the certificate associate data of this TLSA record */
+public final byte []
+getCertificateAssociationData() {
+	return certificateAssociationData;
+}
+
+}
diff --git a/src/org/xbill/DNS/TSIG.java b/src/org/xbill/DNS/TSIG.java
new file mode 100644
index 0000000..d9e6972
--- /dev/null
+++ b/src/org/xbill/DNS/TSIG.java
@@ -0,0 +1,592 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * Transaction signature handling.  This class generates and verifies
+ * TSIG records on messages, which provide transaction security.
+ * @see TSIGRecord
+ *
+ * @author Brian Wellington
+ */
+
+public class TSIG {
+
+private static final String HMAC_MD5_STR = "HMAC-MD5.SIG-ALG.REG.INT.";
+private static final String HMAC_SHA1_STR = "hmac-sha1.";
+private static final String HMAC_SHA224_STR = "hmac-sha224.";
+private static final String HMAC_SHA256_STR = "hmac-sha256.";
+private static final String HMAC_SHA384_STR = "hmac-sha384.";
+private static final String HMAC_SHA512_STR = "hmac-sha512.";
+
+/** The domain name representing the HMAC-MD5 algorithm. */
+public static final Name HMAC_MD5 = Name.fromConstantString(HMAC_MD5_STR);
+
+/** The domain name representing the HMAC-MD5 algorithm (deprecated). */
+public static final Name HMAC = HMAC_MD5;
+
+/** The domain name representing the HMAC-SHA1 algorithm. */
+public static final Name HMAC_SHA1 = Name.fromConstantString(HMAC_SHA1_STR);
+
+/**
+ * The domain name representing the HMAC-SHA224 algorithm.
+ * Note that SHA224 is not supported by Java out-of-the-box, this requires use
+ * of a third party provider like BouncyCastle.org.
+ */
+public static final Name HMAC_SHA224 = Name.fromConstantString(HMAC_SHA224_STR);
+
+/** The domain name representing the HMAC-SHA256 algorithm. */
+public static final Name HMAC_SHA256 = Name.fromConstantString(HMAC_SHA256_STR);
+
+/** The domain name representing the HMAC-SHA384 algorithm. */
+public static final Name HMAC_SHA384 = Name.fromConstantString(HMAC_SHA384_STR);
+
+/** The domain name representing the HMAC-SHA512 algorithm. */
+public static final Name HMAC_SHA512 = Name.fromConstantString(HMAC_SHA512_STR);
+
+/**
+ * The default fudge value for outgoing packets.  Can be overriden by the
+ * tsigfudge option.
+ */
+public static final short FUDGE		= 300;
+
+private Name name, alg;
+private String digest;
+private int digestBlockLength;
+private byte [] key;
+
+private void
+getDigest() {
+	if (alg.equals(HMAC_MD5)) {
+		digest = "md5";
+		digestBlockLength = 64;
+	} else if (alg.equals(HMAC_SHA1)) {
+		digest = "sha-1";
+		digestBlockLength = 64;
+	} else if (alg.equals(HMAC_SHA224)) {
+		digest = "sha-224";
+		digestBlockLength = 64;
+	} else if (alg.equals(HMAC_SHA256)) {
+		digest = "sha-256";
+		digestBlockLength = 64;
+	} else if (alg.equals(HMAC_SHA512)) {
+		digest = "sha-512";
+		digestBlockLength = 128;
+	} else if (alg.equals(HMAC_SHA384)) {
+		digest = "sha-384";
+		digestBlockLength = 128;
+	} else
+		throw new IllegalArgumentException("Invalid algorithm");
+}
+
+/**
+ * Creates a new TSIG key, which can be used to sign or verify a message.
+ * @param algorithm The algorithm of the shared key.
+ * @param name The name of the shared key.
+ * @param key The shared key's data.
+ */
+public
+TSIG(Name algorithm, Name name, byte [] key) {
+	this.name = name;
+	this.alg = algorithm;
+	this.key = key;
+	getDigest();
+}
+
+/**
+ * Creates a new TSIG key with the hmac-md5 algorithm, which can be used to
+ * sign or verify a message.
+ * @param name The name of the shared key.
+ * @param key The shared key's data.
+ */
+public
+TSIG(Name name, byte [] key) {
+	this(HMAC_MD5, name, key);
+}
+
+/**
+ * Creates a new TSIG object, which can be used to sign or verify a message.
+ * @param name The name of the shared key.
+ * @param key The shared key's data represented as a base64 encoded string.
+ * @throws IllegalArgumentException The key name is an invalid name
+ * @throws IllegalArgumentException The key data is improperly encoded
+ */
+public
+TSIG(Name algorithm, String name, String key) {
+	this.key = base64.fromString(key);
+	if (this.key == null)
+		throw new IllegalArgumentException("Invalid TSIG key string");
+	try {
+		this.name = Name.fromString(name, Name.root);
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException("Invalid TSIG key name");
+	}
+	this.alg = algorithm;
+	getDigest();
+}
+
+/**
+ * Creates a new TSIG object, which can be used to sign or verify a message.
+ * @param name The name of the shared key.
+ * @param algorithm The algorithm of the shared key.  The legal values are
+ * "hmac-md5", "hmac-sha1", "hmac-sha224", "hmac-sha256", "hmac-sha384", and
+ * "hmac-sha512".
+ * @param key The shared key's data represented as a base64 encoded string.
+ * @throws IllegalArgumentException The key name is an invalid name
+ * @throws IllegalArgumentException The key data is improperly encoded
+ */
+public
+TSIG(String algorithm, String name, String key) {
+	this(HMAC_MD5, name, key);
+	if (algorithm.equalsIgnoreCase("hmac-md5"))
+		this.alg = HMAC_MD5;
+	else if (algorithm.equalsIgnoreCase("hmac-sha1"))
+		this.alg = HMAC_SHA1;
+	else if (algorithm.equalsIgnoreCase("hmac-sha224"))
+		this.alg = HMAC_SHA224;
+	else if (algorithm.equalsIgnoreCase("hmac-sha256"))
+		this.alg = HMAC_SHA256;
+	else if (algorithm.equalsIgnoreCase("hmac-sha384"))
+		this.alg = HMAC_SHA384;
+	else if (algorithm.equalsIgnoreCase("hmac-sha512"))
+		this.alg = HMAC_SHA512;
+	else
+		throw new IllegalArgumentException("Invalid TSIG algorithm");
+	getDigest();
+}
+
+/**
+ * Creates a new TSIG object with the hmac-md5 algorithm, which can be used to
+ * sign or verify a message.
+ * @param name The name of the shared key
+ * @param key The shared key's data, represented as a base64 encoded string.
+ * @throws IllegalArgumentException The key name is an invalid name
+ * @throws IllegalArgumentException The key data is improperly encoded
+ */
+public
+TSIG(String name, String key) {
+	this(HMAC_MD5, name, key);
+}
+
+/**
+ * Creates a new TSIG object, which can be used to sign or verify a message.
+ * @param str The TSIG key, in the form name:secret, name/secret,
+ * alg:name:secret, or alg/name/secret.  If an algorithm is specified, it must
+ * be "hmac-md5", "hmac-sha1", or "hmac-sha256".
+ * @throws IllegalArgumentException The string does not contain both a name
+ * and secret.
+ * @throws IllegalArgumentException The key name is an invalid name
+ * @throws IllegalArgumentException The key data is improperly encoded
+ */
+static public TSIG
+fromString(String str) {
+	String [] parts = str.split("[:/]", 3);
+	if (parts.length < 2)
+		throw new IllegalArgumentException("Invalid TSIG key " +
+						   "specification");
+	if (parts.length == 3) {
+		try {
+			return new TSIG(parts[0], parts[1], parts[2]);
+		} catch (IllegalArgumentException e) {
+			parts = str.split("[:/]", 2);
+		}
+	}
+	return new TSIG(HMAC_MD5, parts[0], parts[1]);
+}
+
+/**
+ * Generates a TSIG record with a specific error for a message that has
+ * been rendered.
+ * @param m The message
+ * @param b The rendered message
+ * @param error The error
+ * @param old If this message is a response, the TSIG from the request
+ * @return The TSIG record to be added to the message
+ */
+public TSIGRecord
+generate(Message m, byte [] b, int error, TSIGRecord old) {
+	Date timeSigned;
+	if (error != Rcode.BADTIME)
+		timeSigned = new Date();
+	else
+		timeSigned = old.getTimeSigned();
+	int fudge;
+	HMAC hmac = null;
+	if (error == Rcode.NOERROR || error == Rcode.BADTIME)
+		hmac = new HMAC(digest, digestBlockLength, key);
+
+	fudge = Options.intValue("tsigfudge");
+	if (fudge < 0 || fudge > 0x7FFF)
+		fudge = FUDGE;
+
+	if (old != null) {
+		DNSOutput out = new DNSOutput();
+		out.writeU16(old.getSignature().length);
+		if (hmac != null) {
+			hmac.update(out.toByteArray());
+			hmac.update(old.getSignature());
+		}
+	}
+
+	/* Digest the message */
+	if (hmac != null)
+		hmac.update(b);
+
+	DNSOutput out = new DNSOutput();
+	name.toWireCanonical(out);
+	out.writeU16(DClass.ANY);	/* class */
+	out.writeU32(0);		/* ttl */
+	alg.toWireCanonical(out);
+	long time = timeSigned.getTime() / 1000;
+	int timeHigh = (int) (time >> 32);
+	long timeLow = (time & 0xFFFFFFFFL);
+	out.writeU16(timeHigh);
+	out.writeU32(timeLow);
+	out.writeU16(fudge);
+
+	out.writeU16(error);
+	out.writeU16(0); /* No other data */
+
+	if (hmac != null)
+		hmac.update(out.toByteArray());
+
+	byte [] signature;
+	if (hmac != null)
+		signature = hmac.sign();
+	else
+		signature = new byte[0];
+
+	byte [] other = null;
+	if (error == Rcode.BADTIME) {
+		out = new DNSOutput();
+		time = new Date().getTime() / 1000;
+		timeHigh = (int) (time >> 32);
+		timeLow = (time & 0xFFFFFFFFL);
+		out.writeU16(timeHigh);
+		out.writeU32(timeLow);
+		other = out.toByteArray();
+	}
+
+	return (new TSIGRecord(name, DClass.ANY, 0, alg, timeSigned, fudge,
+			       signature, m.getHeader().getID(), error, other));
+}
+
+/**
+ * Generates a TSIG record with a specific error for a message and adds it
+ * to the message.
+ * @param m The message
+ * @param error The error
+ * @param old If this message is a response, the TSIG from the request
+ */
+public void
+apply(Message m, int error, TSIGRecord old) {
+	Record r = generate(m, m.toWire(), error, old);
+	m.addRecord(r, Section.ADDITIONAL);
+	m.tsigState = Message.TSIG_SIGNED;
+}
+
+/**
+ * Generates a TSIG record for a message and adds it to the message
+ * @param m The message
+ * @param old If this message is a response, the TSIG from the request
+ */
+public void
+apply(Message m, TSIGRecord old) {
+	apply(m, Rcode.NOERROR, old);
+}
+
+/**
+ * Generates a TSIG record for a message and adds it to the message
+ * @param m The message
+ * @param old If this message is a response, the TSIG from the request
+ */
+public void
+applyStream(Message m, TSIGRecord old, boolean first) {
+	if (first) {
+		apply(m, old);
+		return;
+	}
+	Date timeSigned = new Date();
+	int fudge;
+	HMAC hmac = new HMAC(digest, digestBlockLength, key);
+
+	fudge = Options.intValue("tsigfudge");
+	if (fudge < 0 || fudge > 0x7FFF)
+		fudge = FUDGE;
+
+	DNSOutput out = new DNSOutput();
+	out.writeU16(old.getSignature().length);
+	hmac.update(out.toByteArray());
+	hmac.update(old.getSignature());
+
+	/* Digest the message */
+	hmac.update(m.toWire());
+
+	out = new DNSOutput();
+	long time = timeSigned.getTime() / 1000;
+	int timeHigh = (int) (time >> 32);
+	long timeLow = (time & 0xFFFFFFFFL);
+	out.writeU16(timeHigh);
+	out.writeU32(timeLow);
+	out.writeU16(fudge);
+
+	hmac.update(out.toByteArray());
+
+	byte [] signature = hmac.sign();
+	byte [] other = null;
+
+	Record r = new TSIGRecord(name, DClass.ANY, 0, alg, timeSigned, fudge,
+				  signature, m.getHeader().getID(),
+				  Rcode.NOERROR, other);
+	m.addRecord(r, Section.ADDITIONAL);
+	m.tsigState = Message.TSIG_SIGNED;
+}
+
+/**
+ * Verifies a TSIG record on an incoming message.  Since this is only called
+ * in the context where a TSIG is expected to be present, it is an error
+ * if one is not present.  After calling this routine, Message.isVerified() may
+ * be called on this message.
+ * @param m The message
+ * @param b An array containing the message in unparsed form.  This is
+ * necessary since TSIG signs the message in wire format, and we can't
+ * recreate the exact wire format (with the same name compression).
+ * @param length The length of the message in the array.
+ * @param old If this message is a response, the TSIG from the request
+ * @return The result of the verification (as an Rcode)
+ * @see Rcode
+ */
+public byte
+verify(Message m, byte [] b, int length, TSIGRecord old) {
+	m.tsigState = Message.TSIG_FAILED;
+	TSIGRecord tsig = m.getTSIG();
+	HMAC hmac = new HMAC(digest, digestBlockLength, key);
+	if (tsig == null)
+		return Rcode.FORMERR;
+
+	if (!tsig.getName().equals(name) || !tsig.getAlgorithm().equals(alg)) {
+		if (Options.check("verbose"))
+			System.err.println("BADKEY failure");
+		return Rcode.BADKEY;
+	}
+	long now = System.currentTimeMillis();
+	long then = tsig.getTimeSigned().getTime();
+	long fudge = tsig.getFudge();
+	if (Math.abs(now - then) > fudge * 1000) {
+		if (Options.check("verbose"))
+			System.err.println("BADTIME failure");
+		return Rcode.BADTIME;
+	}
+
+	if (old != null && tsig.getError() != Rcode.BADKEY &&
+	    tsig.getError() != Rcode.BADSIG)
+	{
+		DNSOutput out = new DNSOutput();
+		out.writeU16(old.getSignature().length);
+		hmac.update(out.toByteArray());
+		hmac.update(old.getSignature());
+	}
+	m.getHeader().decCount(Section.ADDITIONAL);
+	byte [] header = m.getHeader().toWire();
+	m.getHeader().incCount(Section.ADDITIONAL);
+	hmac.update(header);
+
+	int len = m.tsigstart - header.length;	
+	hmac.update(b, header.length, len);
+
+	DNSOutput out = new DNSOutput();
+	tsig.getName().toWireCanonical(out);
+	out.writeU16(tsig.dclass);
+	out.writeU32(tsig.ttl);
+	tsig.getAlgorithm().toWireCanonical(out);
+	long time = tsig.getTimeSigned().getTime() / 1000;
+	int timeHigh = (int) (time >> 32);
+	long timeLow = (time & 0xFFFFFFFFL);
+	out.writeU16(timeHigh);
+	out.writeU32(timeLow);
+	out.writeU16(tsig.getFudge());
+	out.writeU16(tsig.getError());
+	if (tsig.getOther() != null) {
+		out.writeU16(tsig.getOther().length);
+		out.writeByteArray(tsig.getOther());
+	} else {
+		out.writeU16(0);
+	}
+
+	hmac.update(out.toByteArray());
+
+	byte [] signature = tsig.getSignature();
+	int digestLength = hmac.digestLength();
+	int minDigestLength = digest.equals("md5") ? 10 : digestLength / 2;
+
+	if (signature.length > digestLength) {
+		if (Options.check("verbose"))
+			System.err.println("BADSIG: signature too long");
+		return Rcode.BADSIG;
+	} else if (signature.length < minDigestLength) {
+		if (Options.check("verbose"))
+			System.err.println("BADSIG: signature too short");
+		return Rcode.BADSIG;
+	} else if (!hmac.verify(signature, true)) {
+		if (Options.check("verbose"))
+			System.err.println("BADSIG: signature verification");
+		return Rcode.BADSIG;
+	}
+
+	m.tsigState = Message.TSIG_VERIFIED;
+	return Rcode.NOERROR;
+}
+
+/**
+ * Verifies a TSIG record on an incoming message.  Since this is only called
+ * in the context where a TSIG is expected to be present, it is an error
+ * if one is not present.  After calling this routine, Message.isVerified() may
+ * be called on this message.
+ * @param m The message
+ * @param b The message in unparsed form.  This is necessary since TSIG
+ * signs the message in wire format, and we can't recreate the exact wire
+ * format (with the same name compression).
+ * @param old If this message is a response, the TSIG from the request
+ * @return The result of the verification (as an Rcode)
+ * @see Rcode
+ */
+public int
+verify(Message m, byte [] b, TSIGRecord old) {
+	return verify(m, b, b.length, old);
+}
+
+/**
+ * Returns the maximum length of a TSIG record generated by this key.
+ * @see TSIGRecord
+ */
+public int
+recordLength() {
+	return (name.length() + 10 +
+		alg.length() +
+		8 +	// time signed, fudge
+		18 +	// 2 byte MAC length, 16 byte MAC
+		4 +	// original id, error
+		8);	// 2 byte error length, 6 byte max error field.
+}
+
+public static class StreamVerifier {
+	/**
+	 * A helper class for verifying multiple message responses.
+	 */
+
+	private TSIG key;
+	private HMAC verifier;
+	private int nresponses;
+	private int lastsigned;
+	private TSIGRecord lastTSIG;
+
+	/** Creates an object to verify a multiple message response */
+	public
+	StreamVerifier(TSIG tsig, TSIGRecord old) {
+		key = tsig;
+		verifier = new HMAC(key.digest, key.digestBlockLength, key.key);
+		nresponses = 0;
+		lastTSIG = old;
+	}
+
+	/**
+	 * Verifies a TSIG record on an incoming message that is part of a
+	 * multiple message response.
+	 * TSIG records must be present on the first and last messages, and
+	 * at least every 100 records in between.
+	 * After calling this routine, Message.isVerified() may be called on
+	 * this message.
+	 * @param m The message
+	 * @param b The message in unparsed form
+	 * @return The result of the verification (as an Rcode)
+	 * @see Rcode
+	 */
+	public int
+	verify(Message m, byte [] b) {
+		TSIGRecord tsig = m.getTSIG();
+	
+		nresponses++;
+
+		if (nresponses == 1) {
+			int result = key.verify(m, b, lastTSIG);
+			if (result == Rcode.NOERROR) {
+				byte [] signature = tsig.getSignature();
+				DNSOutput out = new DNSOutput();
+				out.writeU16(signature.length);
+				verifier.update(out.toByteArray());
+				verifier.update(signature);
+			}
+			lastTSIG = tsig;
+			return result;
+		}
+
+		if (tsig != null)
+			m.getHeader().decCount(Section.ADDITIONAL);
+		byte [] header = m.getHeader().toWire();
+		if (tsig != null)
+			m.getHeader().incCount(Section.ADDITIONAL);
+		verifier.update(header);
+
+		int len;
+		if (tsig == null)
+			len = b.length - header.length;
+		else
+			len = m.tsigstart - header.length;
+		verifier.update(b, header.length, len);
+
+		if (tsig != null) {
+			lastsigned = nresponses;
+			lastTSIG = tsig;
+		}
+		else {
+			boolean required = (nresponses - lastsigned >= 100);
+			if (required) {
+				m.tsigState = Message.TSIG_FAILED;
+				return Rcode.FORMERR;
+			} else {
+				m.tsigState = Message.TSIG_INTERMEDIATE;
+				return Rcode.NOERROR;
+			}
+		}
+
+		if (!tsig.getName().equals(key.name) ||
+		    !tsig.getAlgorithm().equals(key.alg))
+		{
+			if (Options.check("verbose"))
+				System.err.println("BADKEY failure");
+			m.tsigState = Message.TSIG_FAILED;
+			return Rcode.BADKEY;
+		}
+
+		DNSOutput out = new DNSOutput();
+		long time = tsig.getTimeSigned().getTime() / 1000;
+		int timeHigh = (int) (time >> 32);
+		long timeLow = (time & 0xFFFFFFFFL);
+		out.writeU16(timeHigh);
+		out.writeU32(timeLow);
+		out.writeU16(tsig.getFudge());
+		verifier.update(out.toByteArray());
+
+		if (verifier.verify(tsig.getSignature()) == false) {
+			if (Options.check("verbose"))
+				System.err.println("BADSIG failure");
+			m.tsigState = Message.TSIG_FAILED;
+			return Rcode.BADSIG;
+		}
+
+		verifier.clear();
+		out = new DNSOutput();
+		out.writeU16(tsig.getSignature().length);
+		verifier.update(out.toByteArray());
+		verifier.update(tsig.getSignature());
+
+		m.tsigState = Message.TSIG_VERIFIED;
+		return Rcode.NOERROR;
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/TSIGRecord.java b/src/org/xbill/DNS/TSIGRecord.java
new file mode 100644
index 0000000..c7ce9ed
--- /dev/null
+++ b/src/org/xbill/DNS/TSIGRecord.java
@@ -0,0 +1,220 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+import org.xbill.DNS.utils.*;
+
+/**
+ * Transaction Signature - this record is automatically generated by the
+ * resolver.  TSIG records provide transaction security between the
+ * sender and receiver of a message, using a shared key.
+ * @see Resolver
+ * @see TSIG
+ *
+ * @author Brian Wellington
+ */
+
+public class TSIGRecord extends Record {
+
+private static final long serialVersionUID = -88820909016649306L;
+
+private Name alg;
+private Date timeSigned;
+private int fudge;
+private byte [] signature;
+private int originalID;
+private int error;
+private byte [] other;
+
+TSIGRecord() {} 
+
+Record
+getObject() {
+	return new TSIGRecord();
+}
+
+/**
+ * Creates a TSIG Record from the given data.  This is normally called by
+ * the TSIG class
+ * @param alg The shared key's algorithm
+ * @param timeSigned The time that this record was generated
+ * @param fudge The fudge factor for time - if the time that the message is
+ * received is not in the range [now - fudge, now + fudge], the signature
+ * fails
+ * @param signature The signature
+ * @param originalID The message ID at the time of its generation
+ * @param error The extended error field.  Should be 0 in queries.
+ * @param other The other data field.  Currently used only in BADTIME
+ * responses.
+ * @see TSIG
+ */
+public
+TSIGRecord(Name name, int dclass, long ttl, Name alg, Date timeSigned,
+	   int fudge, byte [] signature, int originalID, int error,
+	   byte other[])
+{
+	super(name, Type.TSIG, dclass, ttl);
+	this.alg = checkName("alg", alg);
+	this.timeSigned = timeSigned;
+	this.fudge = checkU16("fudge", fudge);
+	this.signature = signature;
+	this.originalID = checkU16("originalID", originalID);
+	this.error = checkU16("error", error);
+	this.other = other;
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	alg = new Name(in);
+
+	long timeHigh = in.readU16();
+	long timeLow = in.readU32();
+	long time = (timeHigh << 32) + timeLow;
+	timeSigned = new Date(time * 1000);
+	fudge = in.readU16();
+
+	int sigLen = in.readU16();
+	signature = in.readByteArray(sigLen);
+
+	originalID = in.readU16();
+	error = in.readU16();
+
+	int otherLen = in.readU16();
+	if (otherLen > 0)
+		other = in.readByteArray(otherLen);
+	else
+		other = null;
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	throw st.exception("no text format defined for TSIG");
+}
+
+/** Converts rdata to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(alg);
+	sb.append(" ");
+	if (Options.check("multiline"))
+		sb.append("(\n\t");
+
+	sb.append (timeSigned.getTime() / 1000);
+	sb.append (" ");
+	sb.append (fudge);
+	sb.append (" ");
+	sb.append (signature.length);
+	if (Options.check("multiline")) {
+		sb.append ("\n");
+		sb.append (base64.formatString(signature, 64, "\t", false));
+	} else {
+		sb.append (" ");
+		sb.append (base64.toString(signature));
+	}
+	sb.append (" ");
+	sb.append (Rcode.TSIGstring(error));
+	sb.append (" ");
+	if (other == null)
+		sb.append (0);
+	else {
+		sb.append (other.length);
+		if (Options.check("multiline"))
+			sb.append("\n\n\n\t");
+		else
+			sb.append(" ");
+		if (error == Rcode.BADTIME) {
+			if (other.length != 6) {
+				sb.append("<invalid BADTIME other data>");
+			} else {
+				long time = ((long)(other[0] & 0xFF) << 40) +
+					    ((long)(other[1] & 0xFF) << 32) +
+					    ((other[2] & 0xFF) << 24) +
+					    ((other[3] & 0xFF) << 16) +
+					    ((other[4] & 0xFF) << 8) +
+					    ((other[5] & 0xFF)     );
+				sb.append("<server time: ");
+				sb.append(new Date(time * 1000));
+				sb.append(">");
+			}
+		} else {
+			sb.append("<");
+			sb.append(base64.toString(other));
+			sb.append(">");
+		}
+	}
+	if (Options.check("multiline"))
+		sb.append(" )");
+	return sb.toString();
+}
+
+/** Returns the shared key's algorithm */
+public Name
+getAlgorithm() {
+	return alg;
+}
+
+/** Returns the time that this record was generated */
+public Date
+getTimeSigned() {
+	return timeSigned;
+}
+
+/** Returns the time fudge factor */
+public int
+getFudge() {
+	return fudge;
+}
+
+/** Returns the signature */
+public byte []
+getSignature() {
+	return signature;
+}
+
+/** Returns the original message ID */
+public int
+getOriginalID() {
+	return originalID;
+}
+
+/** Returns the extended error */
+public int
+getError() {
+	return error;
+}
+
+/** Returns the other data */
+public byte []
+getOther() {
+	return other;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	alg.toWire(out, null, canonical);
+
+	long time = timeSigned.getTime() / 1000;
+	int timeHigh = (int) (time >> 32);
+	long timeLow = (time & 0xFFFFFFFFL);
+	out.writeU16(timeHigh);
+	out.writeU32(timeLow);
+	out.writeU16(fudge);
+
+	out.writeU16(signature.length);
+	out.writeByteArray(signature);
+
+	out.writeU16(originalID);
+	out.writeU16(error);
+
+	if (other != null) {
+		out.writeU16(other.length);
+		out.writeByteArray(other);
+	}
+	else
+		out.writeU16(0);
+}
+
+}
diff --git a/src/org/xbill/DNS/TTL.java b/src/org/xbill/DNS/TTL.java
new file mode 100644
index 0000000..01bf416
--- /dev/null
+++ b/src/org/xbill/DNS/TTL.java
@@ -0,0 +1,113 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Routines for parsing BIND-style TTL values.  These values consist of
+ * numbers followed by 1 letter units of time (W - week, D - day, H - hour,
+ * M - minute, S - second).
+ *
+ * @author Brian Wellington
+ */
+
+public final class TTL {
+
+public static final long MAX_VALUE = 0x7FFFFFFFL;
+
+private
+TTL() {}
+
+static void
+check(long i) {
+	if (i < 0 || i > MAX_VALUE)
+		throw new InvalidTTLException(i);
+}
+
+/**
+ * Parses a TTL-like value, which can either be expressed as a number or a
+ * BIND-style string with numbers and units.
+ * @param s The string representing the numeric value.
+ * @param clamp Whether to clamp values in the range [MAX_VALUE + 1, 2^32 -1]
+ * to MAX_VALUE.  This should be donw for TTLs, but not other values which
+ * can be expressed in this format.
+ * @return The value as a number of seconds
+ * @throws NumberFormatException The string was not in a valid TTL format.
+ */
+public static long
+parse(String s, boolean clamp) {
+	if (s == null || s.length() == 0 || !Character.isDigit(s.charAt(0)))
+		throw new NumberFormatException();
+	long value = 0;
+	long ttl = 0;
+	for (int i = 0; i < s.length(); i++) {
+		char c = s.charAt(i);
+		long oldvalue = value;
+		if (Character.isDigit(c)) {
+			value = (value * 10) + Character.getNumericValue(c);
+			if (value < oldvalue)
+				throw new NumberFormatException();
+		} else {
+			switch (Character.toUpperCase(c)) {
+				case 'W': value *= 7;
+				case 'D': value *= 24;
+				case 'H': value *= 60;
+				case 'M': value *= 60;
+				case 'S': break;
+				default:  throw new NumberFormatException();
+			}
+			ttl += value;
+			value = 0;
+			if (ttl > 0xFFFFFFFFL)
+				throw new NumberFormatException();
+		}
+	}
+	if (ttl == 0)
+		ttl = value;
+
+	if (ttl > 0xFFFFFFFFL)
+		throw new NumberFormatException();
+	else if (ttl > MAX_VALUE && clamp)
+		ttl = MAX_VALUE;
+	return ttl;
+}
+
+/**
+ * Parses a TTL, which can either be expressed as a number or a BIND-style
+ * string with numbers and units.
+ * @param s The string representing the TTL
+ * @return The TTL as a number of seconds
+ * @throws NumberFormatException The string was not in a valid TTL format.
+ */
+public static long
+parseTTL(String s) {
+	return parse(s, true);
+}
+
+public static String
+format(long ttl) {
+	TTL.check(ttl);
+	StringBuffer sb = new StringBuffer();
+	long secs, mins, hours, days, weeks;
+	secs = ttl % 60;
+	ttl /= 60;
+	mins = ttl % 60;
+	ttl /= 60;
+	hours = ttl % 24;
+	ttl /= 24;
+	days = ttl % 7;
+	ttl /= 7;
+	weeks = ttl;
+	if (weeks > 0)
+		sb.append(weeks + "W");
+	if (days > 0)
+		sb.append(days + "D");
+	if (hours > 0)
+		sb.append(hours + "H");
+	if (mins > 0)
+		sb.append(mins + "M");
+	if (secs > 0 || (weeks == 0 && days == 0 && hours == 0 && mins == 0))
+		sb.append(secs + "S");
+	return sb.toString();
+}
+
+}
diff --git a/src/org/xbill/DNS/TXTBase.java b/src/org/xbill/DNS/TXTBase.java
new file mode 100644
index 0000000..fd99bfb
--- /dev/null
+++ b/src/org/xbill/DNS/TXTBase.java
@@ -0,0 +1,123 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * Implements common functionality for the many record types whose format
+ * is a list of strings.
+ *
+ * @author Brian Wellington
+ */
+
+abstract class TXTBase extends Record {
+
+private static final long serialVersionUID = -4319510507246305931L;
+
+protected List strings;
+
+protected
+TXTBase() {}
+
+protected
+TXTBase(Name name, int type, int dclass, long ttl) {
+	super(name, type, dclass, ttl);
+}
+
+protected
+TXTBase(Name name, int type, int dclass, long ttl, List strings) {
+	super(name, type, dclass, ttl);
+	if (strings == null)
+		throw new IllegalArgumentException("strings must not be null");
+	this.strings = new ArrayList(strings.size());
+	Iterator it = strings.iterator();
+	try {
+		while (it.hasNext()) {
+			String s = (String) it.next();
+			this.strings.add(byteArrayFromString(s));
+		}
+	}
+	catch (TextParseException e) {
+		throw new IllegalArgumentException(e.getMessage());
+	}
+}
+
+protected
+TXTBase(Name name, int type, int dclass, long ttl, String string) {
+	this(name, type, dclass, ttl, Collections.singletonList(string));
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	strings = new ArrayList(2);
+	while (in.remaining() > 0) {
+		byte [] b = in.readCountedString();
+		strings.add(b);
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	strings = new ArrayList(2);
+	while (true) {
+		Tokenizer.Token t = st.get();
+		if (!t.isString())
+			break;
+		try {
+			strings.add(byteArrayFromString(t.value));
+		}
+		catch (TextParseException e) { 
+			throw st.exception(e.getMessage());
+		}
+
+	}
+	st.unget();
+}
+
+/** converts to a String */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	Iterator it = strings.iterator();
+	while (it.hasNext()) {
+		byte [] array = (byte []) it.next();
+		sb.append(byteArrayToString(array, true));
+		if (it.hasNext())
+			sb.append(" ");
+	}
+	return sb.toString();
+}
+
+/**
+ * Returns the text strings
+ * @return A list of Strings corresponding to the text strings.
+ */
+public List
+getStrings() {
+	List list = new ArrayList(strings.size());
+	for (int i = 0; i < strings.size(); i++)
+		list.add(byteArrayToString((byte []) strings.get(i), false));
+	return list;
+}
+
+/**
+ * Returns the text strings
+ * @return A list of byte arrays corresponding to the text strings.
+ */
+public List
+getStringsAsByteArrays() {
+	return strings;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	Iterator it = strings.iterator();
+	while (it.hasNext()) {
+		byte [] b = (byte []) it.next();
+		out.writeCountedString(b);
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/TXTRecord.java b/src/org/xbill/DNS/TXTRecord.java
new file mode 100644
index 0000000..ea5de04
--- /dev/null
+++ b/src/org/xbill/DNS/TXTRecord.java
@@ -0,0 +1,44 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.*;
+
+/**
+ * Text - stores text strings
+ *
+ * @author Brian Wellington
+ */
+
+public class TXTRecord extends TXTBase {
+
+private static final long serialVersionUID = -5780785764284221342L;
+
+TXTRecord() {}
+
+Record
+getObject() {
+	return new TXTRecord();
+}
+
+/**
+ * Creates a TXT Record from the given data
+ * @param strings The text strings
+ * @throws IllegalArgumentException One of the strings has invalid escapes
+ */
+public
+TXTRecord(Name name, int dclass, long ttl, List strings) {
+	super(name, Type.TXT, dclass, ttl, strings);
+}
+
+/**
+ * Creates a TXT Record from the given data
+ * @param string One text string
+ * @throws IllegalArgumentException The string has invalid escapes
+ */
+public
+TXTRecord(Name name, int dclass, long ttl, String string) {
+	super(name, Type.TXT, dclass, ttl, string);
+}
+
+}
diff --git a/src/org/xbill/DNS/TextParseException.java b/src/org/xbill/DNS/TextParseException.java
new file mode 100644
index 0000000..3b9a425
--- /dev/null
+++ b/src/org/xbill/DNS/TextParseException.java
@@ -0,0 +1,25 @@
+// Copyright (c) 2002-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * An exception thrown when unable to parse text.
+ *
+ * @author Brian Wellington
+ */
+
+public class TextParseException extends IOException {
+
+public
+TextParseException() {
+	super();
+}
+
+public
+TextParseException(String s) {
+	super(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/Tokenizer.java b/src/org/xbill/DNS/Tokenizer.java
new file mode 100644
index 0000000..bc637ab
--- /dev/null
+++ b/src/org/xbill/DNS/Tokenizer.java
@@ -0,0 +1,713 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+//
+// Copyright (C) 2003-2004 Nominum, Inc.
+// 
+// Permission to use, copy, modify, and distribute this software for any
+// purpose with or without fee is hereby granted, provided that the above
+// copyright notice and this permission notice appear in all copies.
+//
+// THE SOFTWARE IS PROVIDED "AS IS" AND NOMINUM DISCLAIMS ALL WARRANTIES
+// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL NOMINUM BE LIABLE FOR ANY
+// SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
+// OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+//
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+
+import org.xbill.DNS.utils.*;
+
+/**
+ * Tokenizer is used to parse DNS records and zones from text format,
+ *
+ * @author Brian Wellington
+ * @author Bob Halley
+ */
+
+public class Tokenizer {
+
+private static String delim = " \t\n;()\"";
+private static String quotes = "\"";
+
+/** End of file */
+public static final int EOF		= 0;
+
+/** End of line */
+public static final int EOL		= 1;
+
+/** Whitespace; only returned when wantWhitespace is set */
+public static final int WHITESPACE	= 2;
+
+/** An identifier (unquoted string) */
+public static final int IDENTIFIER	= 3;
+
+/** A quoted string */
+public static final int QUOTED_STRING	= 4;
+
+/** A comment; only returned when wantComment is set */
+public static final int COMMENT		= 5;
+
+private PushbackInputStream is;
+private boolean ungottenToken;
+private int multiline;
+private boolean quoting;
+private String delimiters;
+private Token current;
+private StringBuffer sb;
+private boolean wantClose;
+
+private String filename;
+private int line;
+
+public static class Token {
+	/** The type of token. */
+	public int type;
+
+	/** The value of the token, or null for tokens without values. */
+	public String value;
+
+	private
+	Token() {
+		type = -1;
+		value = null;
+	}
+
+	private Token
+	set(int type, StringBuffer value) {
+		if (type < 0)
+			throw new IllegalArgumentException();
+		this.type = type;
+		this.value = value == null ? null : value.toString();
+		return this;
+	}
+
+	/**
+	 * Converts the token to a string containing a representation useful
+	 * for debugging.
+	 */
+	public String
+	toString() {
+		switch (type) {
+		case EOF:
+			return "<eof>";
+		case EOL:
+			return "<eol>";
+		case WHITESPACE:
+			return "<whitespace>";
+		case IDENTIFIER:
+			return "<identifier: " + value + ">";
+		case QUOTED_STRING:
+			return "<quoted_string: " + value + ">";
+		case COMMENT:
+			return "<comment: " + value + ">";
+		default:
+			return "<unknown>";
+		}
+	}
+
+	/** Indicates whether this token contains a string. */
+	public boolean
+	isString() {
+		return (type == IDENTIFIER || type == QUOTED_STRING);
+	}
+
+	/** Indicates whether this token contains an EOL or EOF. */
+	public boolean
+	isEOL() {
+		return (type == EOL || type == EOF);
+	}
+}
+
+static class TokenizerException extends TextParseException {
+	String message;
+
+	public
+	TokenizerException(String filename, int line, String message) {
+		super(filename + ":" + line + ": " + message);
+		this.message = message;
+	}
+
+	public String
+	getBaseMessage() {
+		return message;
+	}
+}
+
+/**
+ * Creates a Tokenizer from an arbitrary input stream.
+ * @param is The InputStream to tokenize.
+ */
+public
+Tokenizer(InputStream is) {
+	if (!(is instanceof BufferedInputStream))
+		is = new BufferedInputStream(is);
+	this.is = new PushbackInputStream(is, 2);
+	ungottenToken = false;
+	multiline = 0;
+	quoting = false;
+	delimiters = delim;
+	current = new Token();
+	sb = new StringBuffer();
+	filename = "<none>";
+	line = 1;
+}
+
+/**
+ * Creates a Tokenizer from a string.
+ * @param s The String to tokenize.
+ */
+public
+Tokenizer(String s) {
+	this(new ByteArrayInputStream(s.getBytes()));
+}
+
+/**
+ * Creates a Tokenizer from a file.
+ * @param f The File to tokenize.
+ */
+public
+Tokenizer(File f) throws FileNotFoundException {
+	this(new FileInputStream(f));
+	wantClose = true;
+	filename = f.getName();
+}
+
+private int
+getChar() throws IOException {
+	int c = is.read();
+	if (c == '\r') {
+		int next = is.read();
+		if (next != '\n')
+			is.unread(next);
+		c = '\n';
+	}
+	if (c == '\n')
+		line++;
+	return c;
+}
+
+private void
+ungetChar(int c) throws IOException {
+	if (c == -1)
+		return;
+	is.unread(c);
+	if (c == '\n')
+		line--;
+}
+
+private int
+skipWhitespace() throws IOException {
+	int skipped = 0;
+	while (true) {
+		int c = getChar();
+		if (c != ' ' && c != '\t') {
+	                if (!(c == '\n' && multiline > 0)) {
+				ungetChar(c);
+				return skipped;
+			}
+		}
+		skipped++;
+	}
+}
+
+private void
+checkUnbalancedParens() throws TextParseException {
+	if (multiline > 0)
+		throw exception("unbalanced parentheses");
+}
+
+/**
+ * Gets the next token from a tokenizer.
+ * @param wantWhitespace If true, leading whitespace will be returned as a
+ * token.
+ * @param wantComment If true, comments are returned as tokens.
+ * @return The next token in the stream.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public Token
+get(boolean wantWhitespace, boolean wantComment) throws IOException {
+	int type;
+	int c;
+
+	if (ungottenToken) {
+		ungottenToken = false;
+		if (current.type == WHITESPACE) {
+			if (wantWhitespace)
+				return current;
+		} else if (current.type == COMMENT) {
+			if (wantComment)
+				return current;
+		} else {
+			if (current.type == EOL)
+				line++;
+			return current;
+		}
+	}
+	int skipped = skipWhitespace();
+	if (skipped > 0 && wantWhitespace)
+		return current.set(WHITESPACE, null);
+	type = IDENTIFIER;
+	sb.setLength(0);
+	while (true) {
+		c = getChar();
+		if (c == -1 || delimiters.indexOf(c) != -1) {
+			if (c == -1) {
+				if (quoting)
+					throw exception("EOF in " +
+							"quoted string");
+				else if (sb.length() == 0)
+					return current.set(EOF, null);
+				else
+					return current.set(type, sb);
+			}
+			if (sb.length() == 0 && type != QUOTED_STRING) {
+				if (c == '(') {
+					multiline++;
+					skipWhitespace();
+					continue;
+				} else if (c == ')') {
+					if (multiline <= 0)
+						throw exception("invalid " +
+								"close " +
+								"parenthesis");
+					multiline--;
+					skipWhitespace();
+					continue;
+				} else if (c == '"') {
+					if (!quoting) {
+						quoting = true;
+						delimiters = quotes;
+						type = QUOTED_STRING;
+					} else {
+						quoting = false;
+						delimiters = delim;
+						skipWhitespace();
+					}
+					continue;
+				} else if (c == '\n') {
+					return current.set(EOL, null);
+				} else if (c == ';') {
+					while (true) {
+						c = getChar();
+						if (c == '\n' || c == -1)
+							break;
+						sb.append((char)c);
+					}
+					if (wantComment) {
+						ungetChar(c);
+						return current.set(COMMENT, sb);
+					} else if (c == -1 &&
+						   type != QUOTED_STRING)
+					{
+						checkUnbalancedParens();
+						return current.set(EOF, null);
+					} else if (multiline > 0) {
+						skipWhitespace();
+						sb.setLength(0);
+						continue;
+					} else
+						return current.set(EOL, null);
+				} else
+					throw new IllegalStateException();
+			} else
+				ungetChar(c);
+			break;
+		} else if (c == '\\') {
+			c = getChar();
+			if (c == -1)
+				throw exception("unterminated escape sequence");
+			sb.append('\\');
+		} else if (quoting && c == '\n') {
+			throw exception("newline in quoted string");
+		}
+		sb.append((char)c);
+	}
+	if (sb.length() == 0 && type != QUOTED_STRING) {
+		checkUnbalancedParens();
+		return current.set(EOF, null);
+	}
+	return current.set(type, sb);
+}
+
+/**
+ * Gets the next token from a tokenizer, ignoring whitespace and comments.
+ * @return The next token in the stream.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public Token
+get() throws IOException {
+	return get(false, false);
+}
+
+/**
+ * Returns a token to the stream, so that it will be returned by the next call
+ * to get().
+ * @throws IllegalStateException There are already ungotten tokens.
+ */
+public void
+unget() {
+	if (ungottenToken)
+		throw new IllegalStateException
+				("Cannot unget multiple tokens");
+	if (current.type == EOL)
+		line--;
+	ungottenToken = true;
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to a string.
+ * @return The next token in the stream, as a string.
+ * @throws TextParseException The input was invalid or not a string.
+ * @throws IOException An I/O error occurred.
+ */
+public String
+getString() throws IOException {
+	Token next = get();
+	if (!next.isString()) {
+		throw exception("expected a string");
+	}
+	return next.value;
+}
+
+private String
+_getIdentifier(String expected) throws IOException {
+	Token next = get();
+	if (next.type != IDENTIFIER)
+		throw exception("expected " + expected);
+	return next.value;
+}
+
+/**
+ * Gets the next token from a tokenizer, ensures it is an unquoted string,
+ * and converts it to a string.
+ * @return The next token in the stream, as a string.
+ * @throws TextParseException The input was invalid or not an unquoted string.
+ * @throws IOException An I/O error occurred.
+ */
+public String
+getIdentifier() throws IOException {
+	return _getIdentifier("an identifier");
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to a long.
+ * @return The next token in the stream, as a long.
+ * @throws TextParseException The input was invalid or not a long.
+ * @throws IOException An I/O error occurred.
+ */
+public long
+getLong() throws IOException {
+	String next = _getIdentifier("an integer");
+	if (!Character.isDigit(next.charAt(0)))
+		throw exception("expected an integer");
+	try {
+		return Long.parseLong(next);
+	} catch (NumberFormatException e) {
+		throw exception("expected an integer");
+	}
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to an unsigned 32 bit
+ * integer.
+ * @return The next token in the stream, as an unsigned 32 bit integer.
+ * @throws TextParseException The input was invalid or not an unsigned 32
+ * bit integer.
+ * @throws IOException An I/O error occurred.
+ */
+public long
+getUInt32() throws IOException {
+	long l = getLong();
+	if (l < 0 || l > 0xFFFFFFFFL)
+		throw exception("expected an 32 bit unsigned integer");
+	return l;
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to an unsigned 16 bit
+ * integer.
+ * @return The next token in the stream, as an unsigned 16 bit integer.
+ * @throws TextParseException The input was invalid or not an unsigned 16
+ * bit integer.
+ * @throws IOException An I/O error occurred.
+ */
+public int
+getUInt16() throws IOException {
+	long l = getLong();
+	if (l < 0 || l > 0xFFFFL)
+		throw exception("expected an 16 bit unsigned integer");
+	return (int) l;
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to an unsigned 8 bit
+ * integer.
+ * @return The next token in the stream, as an unsigned 8 bit integer.
+ * @throws TextParseException The input was invalid or not an unsigned 8
+ * bit integer.
+ * @throws IOException An I/O error occurred.
+ */
+public int
+getUInt8() throws IOException {
+	long l = getLong();
+	if (l < 0 || l > 0xFFL)
+		throw exception("expected an 8 bit unsigned integer");
+	return (int) l;
+}
+
+/**
+ * Gets the next token from a tokenizer and parses it as a TTL.
+ * @return The next token in the stream, as an unsigned 32 bit integer.
+ * @throws TextParseException The input was not valid.
+ * @throws IOException An I/O error occurred.
+ * @see TTL
+ */
+public long
+getTTL() throws IOException {
+	String next = _getIdentifier("a TTL value");
+	try {
+		return TTL.parseTTL(next);
+	}
+	catch (NumberFormatException e) {
+		throw exception("expected a TTL value");
+	}
+}
+
+/**
+ * Gets the next token from a tokenizer and parses it as if it were a TTL.
+ * @return The next token in the stream, as an unsigned 32 bit integer.
+ * @throws TextParseException The input was not valid.
+ * @throws IOException An I/O error occurred.
+ * @see TTL
+ */
+public long
+getTTLLike() throws IOException {
+	String next = _getIdentifier("a TTL-like value");
+	try {
+		return TTL.parse(next, false);
+	}
+	catch (NumberFormatException e) {
+		throw exception("expected a TTL-like value");
+	}
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to a name.
+ * @param origin The origin to append to relative names.
+ * @return The next token in the stream, as a name.
+ * @throws TextParseException The input was invalid or not a valid name.
+ * @throws IOException An I/O error occurred.
+ * @throws RelativeNameException The parsed name was relative, even with the
+ * origin.
+ * @see Name
+ */
+public Name
+getName(Name origin) throws IOException {
+	String next = _getIdentifier("a name");
+	try {
+		Name name = Name.fromString(next, origin);
+		if (!name.isAbsolute())
+			throw new RelativeNameException(name);
+		return name;
+	}
+	catch (TextParseException e) {
+		throw exception(e.getMessage());
+	}
+}
+
+/**
+ * Gets the next token from a tokenizer and converts it to an IP Address.
+ * @param family The address family.
+ * @return The next token in the stream, as an InetAddress
+ * @throws TextParseException The input was invalid or not a valid address.
+ * @throws IOException An I/O error occurred.
+ * @see Address
+ */
+public InetAddress
+getAddress(int family) throws IOException {
+	String next = _getIdentifier("an address");
+	try {
+		return Address.getByAddress(next, family);
+	}
+	catch (UnknownHostException e) {
+		throw exception(e.getMessage());
+	}
+}
+
+/**
+ * Gets the next token from a tokenizer, which must be an EOL or EOF.
+ * @throws TextParseException The input was invalid or not an EOL or EOF token.
+ * @throws IOException An I/O error occurred.
+ */
+public void
+getEOL() throws IOException {
+	Token next = get();
+	if (next.type != EOL && next.type != EOF) {
+		throw exception("expected EOL or EOF");
+	}
+}
+
+/**
+ * Returns a concatenation of the remaining strings from a Tokenizer.
+ */
+private String
+remainingStrings() throws IOException {
+        StringBuffer buffer = null;
+        while (true) {
+                Tokenizer.Token t = get();
+                if (!t.isString())
+                        break;
+                if (buffer == null)
+                        buffer = new StringBuffer();
+                buffer.append(t.value);
+        }
+        unget();
+        if (buffer == null)
+                return null;
+        return buffer.toString();
+}
+
+/**
+ * Gets the remaining string tokens until an EOL/EOF is seen, concatenates
+ * them together, and converts the base64 encoded data to a byte array.
+ * @param required If true, an exception will be thrown if no strings remain;
+ * otherwise null be be returned.
+ * @return The byte array containing the decoded strings, or null if there
+ * were no strings to decode.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getBase64(boolean required) throws IOException {
+	String s = remainingStrings();
+	if (s == null) {
+		if (required)
+			throw exception("expected base64 encoded string");
+		else
+			return null;
+	}
+	byte [] array = base64.fromString(s);
+	if (array == null)
+		throw exception("invalid base64 encoding");
+	return array;
+}
+
+/**
+ * Gets the remaining string tokens until an EOL/EOF is seen, concatenates
+ * them together, and converts the base64 encoded data to a byte array.
+ * @return The byte array containing the decoded strings, or null if there
+ * were no strings to decode.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getBase64() throws IOException {
+	return getBase64(false);
+}
+
+/**
+ * Gets the remaining string tokens until an EOL/EOF is seen, concatenates
+ * them together, and converts the hex encoded data to a byte array.
+ * @param required If true, an exception will be thrown if no strings remain;
+ * otherwise null be be returned.
+ * @return The byte array containing the decoded strings, or null if there
+ * were no strings to decode.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getHex(boolean required) throws IOException {
+	String s = remainingStrings();
+	if (s == null) {
+		if (required)
+			throw exception("expected hex encoded string");
+		else
+			return null;
+	}
+	byte [] array = base16.fromString(s);
+	if (array == null)
+		throw exception("invalid hex encoding");
+	return array;
+}
+
+/**
+ * Gets the remaining string tokens until an EOL/EOF is seen, concatenates
+ * them together, and converts the hex encoded data to a byte array.
+ * @return The byte array containing the decoded strings, or null if there
+ * were no strings to decode.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getHex() throws IOException {
+	return getHex(false);
+}
+
+/**
+ * Gets the next token from a tokenizer and decodes it as hex.
+ * @return The byte array containing the decoded string.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getHexString() throws IOException {
+	String next = _getIdentifier("a hex string");
+	byte [] array = base16.fromString(next);
+	if (array == null)
+		throw exception("invalid hex encoding");
+	return array;
+}
+
+/**
+ * Gets the next token from a tokenizer and decodes it as base32.
+ * @param b32 The base32 context to decode with.
+ * @return The byte array containing the decoded string.
+ * @throws TextParseException The input was invalid.
+ * @throws IOException An I/O error occurred.
+ */
+public byte []
+getBase32String(base32 b32) throws IOException {
+	String next = _getIdentifier("a base32 string");
+	byte [] array = b32.fromString(next);
+	if (array == null)
+		throw exception("invalid base32 encoding");
+	return array;
+}
+
+/**
+ * Creates an exception which includes the current state in the error message
+ * @param s The error message to include.
+ * @return The exception to be thrown
+ */
+public TextParseException
+exception(String s) {
+	return new TokenizerException(filename, line, s);
+}
+
+/**
+ * Closes any files opened by this tokenizer.
+ */
+public void
+close() {
+	if (wantClose) {
+		try {
+			is.close();
+		}
+		catch (IOException e) {
+		}
+	}
+}
+
+protected void
+finalize() {
+	close();
+}
+
+}
diff --git a/src/org/xbill/DNS/Type.java b/src/org/xbill/DNS/Type.java
new file mode 100644
index 0000000..df84e83
--- /dev/null
+++ b/src/org/xbill/DNS/Type.java
@@ -0,0 +1,361 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.util.HashMap;
+
+/**
+ * Constants and functions relating to DNS Types
+ *
+ * @author Brian Wellington
+ */
+
+public final class Type {
+
+/** Address */
+public static final int A		= 1;
+
+/** Name server */
+public static final int NS		= 2;
+
+/** Mail destination */
+public static final int MD		= 3;
+
+/** Mail forwarder */
+public static final int MF		= 4;
+
+/** Canonical name (alias) */
+public static final int CNAME		= 5;
+
+/** Start of authority */
+public static final int SOA		= 6;
+
+/** Mailbox domain name */
+public static final int MB		= 7;
+
+/** Mail group member */
+public static final int MG		= 8;
+
+/** Mail rename name */
+public static final int MR		= 9;
+
+/** Null record */
+public static final int NULL		= 10;
+
+/** Well known services */
+public static final int WKS		= 11;
+
+/** Domain name pointer */
+public static final int PTR		= 12;
+
+/** Host information */
+public static final int HINFO		= 13;
+
+/** Mailbox information */
+public static final int MINFO		= 14;
+
+/** Mail routing information */
+public static final int MX		= 15;
+
+/** Text strings */
+public static final int TXT		= 16;
+
+/** Responsible person */
+public static final int RP		= 17;
+
+/** AFS cell database */
+public static final int AFSDB		= 18;
+
+/** X.25 calling address */
+public static final int X25		= 19;
+
+/** ISDN calling address */
+public static final int ISDN		= 20;
+
+/** Router */
+public static final int RT		= 21;
+
+/** NSAP address */
+public static final int NSAP		= 22;
+
+/** Reverse NSAP address (deprecated) */
+public static final int NSAP_PTR	= 23;
+
+/** Signature */
+public static final int SIG		= 24;
+
+/** Key */
+public static final int KEY		= 25;
+
+/** X.400 mail mapping */
+public static final int PX		= 26;
+
+/** Geographical position (withdrawn) */
+public static final int GPOS		= 27;
+
+/** IPv6 address */
+public static final int AAAA		= 28;
+
+/** Location */
+public static final int LOC		= 29;
+
+/** Next valid name in zone */
+public static final int NXT		= 30;
+
+/** Endpoint identifier */
+public static final int EID		= 31;
+
+/** Nimrod locator */
+public static final int NIMLOC		= 32;
+
+/** Server selection */
+public static final int SRV		= 33;
+
+/** ATM address */
+public static final int ATMA		= 34;
+
+/** Naming authority pointer */
+public static final int NAPTR		= 35;
+
+/** Key exchange */
+public static final int KX		= 36;
+
+/** Certificate */
+public static final int CERT		= 37;
+
+/** IPv6 address (experimental) */
+public static final int A6		= 38;
+
+/** Non-terminal name redirection */
+public static final int DNAME		= 39;
+
+/** Options - contains EDNS metadata */
+public static final int OPT		= 41;
+
+/** Address Prefix List */
+public static final int APL		= 42;
+
+/** Delegation Signer */
+public static final int DS		= 43;
+
+/** SSH Key Fingerprint */
+public static final int SSHFP		= 44;
+
+/** IPSEC key */
+public static final int IPSECKEY	= 45;
+
+/** Resource Record Signature */
+public static final int RRSIG		= 46;
+
+/** Next Secure Name */
+public static final int NSEC		= 47;
+
+/** DNSSEC Key */
+public static final int DNSKEY		= 48;
+
+/** Dynamic Host Configuration Protocol (DHCP) ID */
+public static final int DHCID		= 49;
+
+/** Next SECure, 3rd edition, RFC 5155 */
+public static final int NSEC3		= 50;
+
+/** Next SECure PARAMeter, RFC 5155 */
+public static final int NSEC3PARAM	= 51;
+
+/** Transport Layer Security Authentication, draft-ietf-dane-protocol-23 */
+public static final int TLSA		= 52;
+
+/** Sender Policy Framework (experimental) */
+public static final int SPF		= 99;
+
+/** Transaction key - used to compute a shared secret or exchange a key */
+public static final int TKEY		= 249;
+
+/** Transaction signature */
+public static final int TSIG		= 250;
+
+/** Incremental zone transfer */
+public static final int IXFR		= 251;
+
+/** Zone transfer */
+public static final int AXFR		= 252;
+
+/** Transfer mailbox records */
+public static final int MAILB		= 253;
+
+/** Transfer mail agent records */
+public static final int MAILA		= 254;
+
+/** Matches any type */
+public static final int ANY		= 255;
+
+/** DNSSEC Lookaside Validation, RFC 4431 . */
+public static final int DLV		= 32769;
+
+
+private static class TypeMnemonic extends Mnemonic {
+	private HashMap objects;
+
+	public
+	TypeMnemonic() {
+		super("Type", CASE_UPPER);
+		setPrefix("TYPE");
+		objects = new HashMap();
+	}
+
+	public void
+	add(int val, String str, Record proto) {
+		super.add(val, str);
+		objects.put(Mnemonic.toInteger(val), proto);
+	}
+	
+	public void
+	check(int val) {
+		Type.check(val);
+	}
+
+	public Record
+	getProto(int val) {
+		check(val);
+		return (Record) objects.get(toInteger(val));
+	}
+}
+
+private static TypeMnemonic types = new TypeMnemonic();
+
+static {
+	types.add(A, "A", new ARecord());
+	types.add(NS, "NS", new NSRecord());
+	types.add(MD, "MD", new MDRecord());
+	types.add(MF, "MF", new MFRecord());
+	types.add(CNAME, "CNAME", new CNAMERecord());
+	types.add(SOA, "SOA", new SOARecord());
+	types.add(MB, "MB", new MBRecord());
+	types.add(MG, "MG", new MGRecord());
+	types.add(MR, "MR", new MRRecord());
+	types.add(NULL, "NULL", new NULLRecord());
+	types.add(WKS, "WKS", new WKSRecord());
+	types.add(PTR, "PTR", new PTRRecord());
+	types.add(HINFO, "HINFO", new HINFORecord());
+	types.add(MINFO, "MINFO", new MINFORecord());
+	types.add(MX, "MX", new MXRecord());
+	types.add(TXT, "TXT", new TXTRecord());
+	types.add(RP, "RP", new RPRecord());
+	types.add(AFSDB, "AFSDB", new AFSDBRecord());
+	types.add(X25, "X25", new X25Record());
+	types.add(ISDN, "ISDN", new ISDNRecord());
+	types.add(RT, "RT", new RTRecord());
+	types.add(NSAP, "NSAP", new NSAPRecord());
+	types.add(NSAP_PTR, "NSAP-PTR", new NSAP_PTRRecord());
+	types.add(SIG, "SIG", new SIGRecord());
+	types.add(KEY, "KEY", new KEYRecord());
+	types.add(PX, "PX", new PXRecord());
+	types.add(GPOS, "GPOS", new GPOSRecord());
+	types.add(AAAA, "AAAA", new AAAARecord());
+	types.add(LOC, "LOC", new LOCRecord());
+	types.add(NXT, "NXT", new NXTRecord());
+	types.add(EID, "EID");
+	types.add(NIMLOC, "NIMLOC");
+	types.add(SRV, "SRV", new SRVRecord());
+	types.add(ATMA, "ATMA");
+	types.add(NAPTR, "NAPTR", new NAPTRRecord());
+	types.add(KX, "KX", new KXRecord());
+	types.add(CERT, "CERT", new CERTRecord());
+	types.add(A6, "A6", new A6Record());
+	types.add(DNAME, "DNAME", new DNAMERecord());
+	types.add(OPT, "OPT", new OPTRecord());
+	types.add(APL, "APL", new APLRecord());
+	types.add(DS, "DS", new DSRecord());
+	types.add(SSHFP, "SSHFP", new SSHFPRecord());
+	types.add(IPSECKEY, "IPSECKEY", new IPSECKEYRecord());
+	types.add(RRSIG, "RRSIG", new RRSIGRecord());
+	types.add(NSEC, "NSEC", new NSECRecord());
+	types.add(DNSKEY, "DNSKEY", new DNSKEYRecord());
+	types.add(DHCID, "DHCID", new DHCIDRecord());
+	types.add(NSEC3, "NSEC3", new NSEC3Record());
+	types.add(NSEC3PARAM, "NSEC3PARAM", new NSEC3PARAMRecord());
+	types.add(TLSA, "TLSA", new TLSARecord());
+	types.add(SPF, "SPF", new SPFRecord());
+	types.add(TKEY, "TKEY", new TKEYRecord());
+	types.add(TSIG, "TSIG", new TSIGRecord());
+	types.add(IXFR, "IXFR");
+	types.add(AXFR, "AXFR");
+	types.add(MAILB, "MAILB");
+	types.add(MAILA, "MAILA");
+	types.add(ANY, "ANY");
+	types.add(DLV, "DLV", new DLVRecord());
+}
+
+private
+Type() {
+}
+
+/**
+ * Checks that a numeric Type is valid.
+ * @throws InvalidTypeException The type is out of range.
+ */
+public static void
+check(int val) {
+	if (val < 0 || val > 0xFFFF)
+		throw new InvalidTypeException(val);
+}
+
+/**
+ * Converts a numeric Type into a String
+ * @param val The type value.
+ * @return The canonical string representation of the type
+ * @throws InvalidTypeException The type is out of range.
+ */
+public static String
+string(int val) {
+	return types.getText(val);
+}
+
+/**
+ * Converts a String representation of an Type into its numeric value.
+ * @param s The string representation of the type
+ * @param numberok Whether a number will be accepted or not.
+ * @return The type code, or -1 on error.
+ */
+public static int
+value(String s, boolean numberok) {
+	int val = types.getValue(s);
+	if (val == -1 && numberok) {
+		val = types.getValue("TYPE" + s);
+	}
+	return val;
+}
+
+/**
+ * Converts a String representation of an Type into its numeric value
+ * @return The type code, or -1 on error.
+ */
+public static int
+value(String s) {
+	return value(s, false);
+}
+
+static Record
+getProto(int val) {
+	return types.getProto(val);
+}
+
+/** Is this type valid for a record (a non-meta type)? */
+public static boolean
+isRR(int type) {
+	switch (type) {
+		case OPT:
+		case TKEY:
+		case TSIG:
+		case IXFR:
+		case AXFR:
+		case MAILB:
+		case MAILA:
+		case ANY:
+			return false;
+		default:
+			return true;
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/TypeBitmap.java b/src/org/xbill/DNS/TypeBitmap.java
new file mode 100644
index 0000000..628cc35
--- /dev/null
+++ b/src/org/xbill/DNS/TypeBitmap.java
@@ -0,0 +1,147 @@
+// Copyright (c) 2004-2009 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * Routines for deal with the lists of types found in NSEC/NSEC3 records.
+ *
+ * @author Brian Wellington
+ */
+
+import java.io.*;
+import java.util.*;
+
+final class TypeBitmap implements Serializable {
+
+private static final long serialVersionUID = -125354057735389003L;
+
+private TreeSet types;
+
+private
+TypeBitmap() {
+	types = new TreeSet();
+}
+
+public
+TypeBitmap(int [] array) {
+	this();
+	for (int i = 0; i < array.length; i++) {
+		Type.check(array[i]);
+		types.add(new Integer(array[i]));
+	}
+}
+
+public
+TypeBitmap(DNSInput in) throws WireParseException {
+	this();
+	int lastbase = -1;
+	while (in.remaining() > 0) {
+		if (in.remaining() < 2)
+			throw new WireParseException
+				("invalid bitmap descriptor");
+		int mapbase = in.readU8();
+		if (mapbase < lastbase)
+			throw new WireParseException("invalid ordering");
+		int maplength = in.readU8();
+		if (maplength > in.remaining())
+			throw new WireParseException("invalid bitmap");
+		for (int i = 0; i < maplength; i++) {
+			int current = in.readU8();
+			if (current == 0)
+				continue;
+			for (int j = 0; j < 8; j++) {
+				if ((current & (1 << (7 - j))) == 0)
+					continue;
+				int typecode = mapbase * 256 + + i * 8 + j;
+				types.add(Mnemonic.toInteger(typecode));
+			}
+		}
+	}
+}
+
+public
+TypeBitmap(Tokenizer st) throws IOException {
+	this();
+	while (true) {
+		Tokenizer.Token t = st.get();
+		if (!t.isString())
+			break;
+		int typecode = Type.value(t.value);
+		if (typecode < 0) {
+			throw st.exception("Invalid type: " + t.value);
+		}
+		types.add(Mnemonic.toInteger(typecode));
+	}
+	st.unget();
+}
+
+public int []
+toArray() {
+	int [] array = new int[types.size()];
+	int n = 0;
+	for (Iterator it = types.iterator(); it.hasNext(); )
+		array[n++] = ((Integer)it.next()).intValue();
+	return array;
+}
+
+public String
+toString() {
+	StringBuffer sb = new StringBuffer();
+	for (Iterator it = types.iterator(); it.hasNext(); ) {
+		int t = ((Integer)it.next()).intValue();
+		sb.append(Type.string(t));
+		if (it.hasNext())
+			sb.append(' ');
+	}
+	return sb.toString();
+}
+
+private static void
+mapToWire(DNSOutput out, TreeSet map, int mapbase) {
+	int arraymax = (((Integer)map.last()).intValue()) & 0xFF;
+	int arraylength = (arraymax / 8) + 1;
+	int [] array = new int[arraylength];
+	out.writeU8(mapbase);
+	out.writeU8(arraylength);
+	for (Iterator it = map.iterator(); it.hasNext(); ) {
+		int typecode = ((Integer)it.next()).intValue();
+		array[(typecode & 0xFF) / 8] |= (1 << ( 7 - typecode % 8));
+	}
+	for (int j = 0; j < arraylength; j++)
+		out.writeU8(array[j]);
+}
+
+public void
+toWire(DNSOutput out) {
+	if (types.size() == 0)
+		return;
+
+	int mapbase = -1;
+	TreeSet map = new TreeSet();
+
+	for (Iterator it = types.iterator(); it.hasNext(); ) {
+		int t = ((Integer)it.next()).intValue();
+		int base = t >> 8;
+		if (base != mapbase) {
+			if (map.size() > 0) {
+				mapToWire(out, map, mapbase);
+				map.clear();
+			}
+			mapbase = base;
+		}
+			map.add(new Integer(t));
+	}
+	mapToWire(out, map, mapbase);
+}
+
+public boolean
+empty() {
+	return types.isEmpty();
+}
+
+public boolean
+contains(int typecode) {
+	return types.contains(Mnemonic.toInteger(typecode));
+}
+
+}
diff --git a/src/org/xbill/DNS/U16NameBase.java b/src/org/xbill/DNS/U16NameBase.java
new file mode 100644
index 0000000..df3c836
--- /dev/null
+++ b/src/org/xbill/DNS/U16NameBase.java
@@ -0,0 +1,75 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * Implements common functionality for the many record types whose format
+ * is an unsigned 16 bit integer followed by a name.
+ *
+ * @author Brian Wellington
+ */
+
+abstract class U16NameBase extends Record {
+
+private static final long serialVersionUID = -8315884183112502995L;
+
+protected int u16Field;
+protected Name nameField;
+
+protected
+U16NameBase() {}
+
+protected
+U16NameBase(Name name, int type, int dclass, long ttl) {
+	super(name, type, dclass, ttl);
+}
+
+protected
+U16NameBase(Name name, int type, int dclass, long ttl, int u16Field,
+	    String u16Description, Name nameField, String nameDescription)
+{
+	super(name, type, dclass, ttl);
+	this.u16Field = checkU16(u16Description, u16Field);
+	this.nameField = checkName(nameDescription, nameField);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	u16Field = in.readU16();
+	nameField = new Name(in);
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	u16Field = st.getUInt16();
+	nameField = st.getName(origin);
+}
+
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(u16Field);
+	sb.append(" ");
+	sb.append(nameField);
+	return sb.toString();
+}
+
+protected int
+getU16Field() {
+	return u16Field;
+}
+
+protected Name
+getNameField() {
+	return nameField;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeU16(u16Field);
+	nameField.toWire(out, null, canonical);
+}
+
+}
diff --git a/src/org/xbill/DNS/UDPClient.java b/src/org/xbill/DNS/UDPClient.java
new file mode 100644
index 0000000..e752ce4
--- /dev/null
+++ b/src/org/xbill/DNS/UDPClient.java
@@ -0,0 +1,164 @@
+// Copyright (c) 2005 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import java.security.SecureRandom;
+import java.nio.*;
+import java.nio.channels.*;
+
+final class UDPClient extends Client {
+
+private static final int EPHEMERAL_START = 1024;
+private static final int EPHEMERAL_STOP  = 65535;
+private static final int EPHEMERAL_RANGE  = EPHEMERAL_STOP - EPHEMERAL_START;
+
+private static SecureRandom prng = new SecureRandom();
+private static volatile boolean prng_initializing = true;
+
+/*
+ * On some platforms (Windows), the SecureRandom module initialization involves
+ * a call to InetAddress.getLocalHost(), which can end up here if using a
+ * dnsjava name service provider.
+ *
+ * This can cause problems in multiple ways.
+ *   - If the SecureRandom seed generation process calls into here, and this
+ *     module attempts to seed the local SecureRandom object, the thread hangs.
+ *   - If something else calls InetAddress.getLocalHost(), and that causes this
+ *     module to seed the local SecureRandom object, the thread hangs.
+ *
+ * To avoid both of these, check at initialization time to see if InetAddress
+ * is in the call chain.  If so, initialize the SecureRandom object in a new
+ * thread, and disable port randomization until it completes.
+ */
+static {
+	new Thread(new Runnable() {
+			   public void run() {
+			   int n = prng.nextInt();
+			   prng_initializing = false;
+		   }}).start();
+}
+
+private boolean bound = false;
+
+public
+UDPClient(long endTime) throws IOException {
+	super(DatagramChannel.open(), endTime);
+}
+
+private void
+bind_random(InetSocketAddress addr) throws IOException
+{
+	if (prng_initializing) {
+		try {
+			Thread.sleep(2);
+		}
+		catch (InterruptedException e) {
+		}
+		if (prng_initializing)
+			return;
+	}
+
+	DatagramChannel channel = (DatagramChannel) key.channel();
+	InetSocketAddress temp;
+
+	for (int i = 0; i < 1024; i++) {
+		try {
+			int port = prng.nextInt(EPHEMERAL_RANGE) +
+				   EPHEMERAL_START;
+			if (addr != null)
+				temp = new InetSocketAddress(addr.getAddress(),
+							     port);
+			else
+				temp = new InetSocketAddress(port);
+			channel.socket().bind(temp);
+			bound = true;
+			return;
+		}
+		catch (SocketException e) {
+		}
+	}
+}
+
+void
+bind(SocketAddress addr) throws IOException {
+	if (addr == null ||
+	    (addr instanceof InetSocketAddress &&
+	     ((InetSocketAddress)addr).getPort() == 0))
+	{
+		bind_random((InetSocketAddress) addr);
+		if (bound)
+			return;
+	}
+
+	if (addr != null) {
+		DatagramChannel channel = (DatagramChannel) key.channel();
+		channel.socket().bind(addr);
+		bound = true;
+	}
+}
+
+void
+connect(SocketAddress addr) throws IOException {
+	if (!bound)
+		bind(null);
+	DatagramChannel channel = (DatagramChannel) key.channel();
+	channel.connect(addr);
+}
+
+void
+send(byte [] data) throws IOException {
+	DatagramChannel channel = (DatagramChannel) key.channel();
+	verboseLog("UDP write", data);
+	channel.write(ByteBuffer.wrap(data));
+}
+
+byte []
+recv(int max) throws IOException {
+	DatagramChannel channel = (DatagramChannel) key.channel();
+	byte [] temp = new byte[max];
+	key.interestOps(SelectionKey.OP_READ);
+	try {
+		while (!key.isReadable())
+			blockUntil(key, endTime);
+	}
+	finally {
+		if (key.isValid())
+			key.interestOps(0);
+	}
+	long ret = channel.read(ByteBuffer.wrap(temp));
+	if (ret <= 0)
+		throw new EOFException();
+	int len = (int) ret;
+	byte [] data = new byte[len];
+	System.arraycopy(temp, 0, data, 0, len);
+	verboseLog("UDP read", data);
+	return data;
+}
+
+static byte []
+sendrecv(SocketAddress local, SocketAddress remote, byte [] data, int max,
+	 long endTime)
+throws IOException
+{
+	UDPClient client = new UDPClient(endTime);
+	try {
+		client.bind(local);
+		client.connect(remote);
+		client.send(data);
+		return client.recv(max);
+	}
+	finally {
+		client.cleanup();
+	}
+}
+
+static byte []
+sendrecv(SocketAddress addr, byte [] data, int max, long endTime)
+throws IOException
+{
+	return sendrecv(null, addr, data, max, endTime);
+}
+
+}
diff --git a/src/org/xbill/DNS/UNKRecord.java b/src/org/xbill/DNS/UNKRecord.java
new file mode 100644
index 0000000..91c9697
--- /dev/null
+++ b/src/org/xbill/DNS/UNKRecord.java
@@ -0,0 +1,54 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * A class implementing Records of unknown and/or unimplemented types.  This
+ * class can only be initialized using static Record initializers.
+ *
+ * @author Brian Wellington
+ */
+
+public class UNKRecord extends Record {
+
+private static final long serialVersionUID = -4193583311594626915L;
+
+private byte [] data;
+
+UNKRecord() {}
+
+Record
+getObject() {
+	return new UNKRecord();
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	data = in.readByteArray();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	throw st.exception("invalid unknown RR encoding");
+}
+
+/** Converts this Record to the String "unknown format" */
+String
+rrToString() {
+	return unknownToString(data);
+}
+
+/** Returns the contents of this record. */
+public byte []
+getData() { 
+	return data;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(data);
+}
+
+}
diff --git a/src/org/xbill/DNS/Update.java b/src/org/xbill/DNS/Update.java
new file mode 100644
index 0000000..02a920b
--- /dev/null
+++ b/src/org/xbill/DNS/Update.java
@@ -0,0 +1,300 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A helper class for constructing dynamic DNS (DDNS) update messages.
+ *
+ * @author Brian Wellington
+ */
+
+public class Update extends Message {
+
+private Name origin;
+private int dclass;
+
+/**
+ * Creates an update message.
+ * @param zone The name of the zone being updated.
+ * @param dclass The class of the zone being updated.
+ */
+public
+Update(Name zone, int dclass) {
+	super();
+	if (!zone.isAbsolute())
+		throw new RelativeNameException(zone);
+	DClass.check(dclass);
+        getHeader().setOpcode(Opcode.UPDATE);
+	Record soa = Record.newRecord(zone, Type.SOA, DClass.IN);
+	addRecord(soa, Section.QUESTION);
+	this.origin = zone;
+	this.dclass = dclass;
+}
+
+/**
+ * Creates an update message.  The class is assumed to be IN.
+ * @param zone The name of the zone being updated.
+ */
+public
+Update(Name zone) {
+	this(zone, DClass.IN);
+}
+
+private void
+newPrereq(Record rec) {
+	addRecord(rec, Section.PREREQ);
+}
+
+private void
+newUpdate(Record rec) {
+	addRecord(rec, Section.UPDATE);
+}
+
+/**
+ * Inserts a prerequisite that the specified name exists; that is, there
+ * exist records with the given name in the zone.
+ */
+public void
+present(Name name) {
+	newPrereq(Record.newRecord(name, Type.ANY, DClass.ANY, 0));
+}
+
+/**
+ * Inserts a prerequisite that the specified rrset exists; that is, there
+ * exist records with the given name and type in the zone.
+ */
+public void
+present(Name name, int type) {
+	newPrereq(Record.newRecord(name, type, DClass.ANY, 0));
+}
+
+/**
+ * Parses a record from the string, and inserts a prerequisite that the
+ * record exists.  Due to the way value-dependent prequisites work, the
+ * condition that must be met is that the set of all records with the same 
+ * and type in the update message must be identical to the set of all records
+ * with that name and type on the server.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+present(Name name, int type, String record) throws IOException {
+	newPrereq(Record.fromString(name, type, dclass, 0, record, origin));
+}
+
+/**
+ * Parses a record from the tokenizer, and inserts a prerequisite that the
+ * record exists.  Due to the way value-dependent prequisites work, the
+ * condition that must be met is that the set of all records with the same 
+ * and type in the update message must be identical to the set of all records
+ * with that name and type on the server.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+present(Name name, int type, Tokenizer tokenizer) throws IOException {
+	newPrereq(Record.fromString(name, type, dclass, 0, tokenizer, origin));
+}
+
+/**
+ * Inserts a prerequisite that the specified record exists.  Due to the way
+ * value-dependent prequisites work, the condition that must be met is that
+ * the set of all records with the same and type in the update message must
+ * be identical to the set of all records with that name and type on the server.
+ */
+public void
+present(Record record) {
+	newPrereq(record);
+}
+
+/**
+ * Inserts a prerequisite that the specified name does not exist; that is,
+ * there are no records with the given name in the zone.
+ */
+public void
+absent(Name name) {
+	newPrereq(Record.newRecord(name, Type.ANY, DClass.NONE, 0));
+}
+
+/**
+ * Inserts a prerequisite that the specified rrset does not exist; that is,
+ * there are no records with the given name and type in the zone.
+ */
+public void
+absent(Name name, int type) {
+	newPrereq(Record.newRecord(name, type, DClass.NONE, 0));
+}
+
+/**
+ * Parses a record from the string, and indicates that the record
+ * should be inserted into the zone.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+add(Name name, int type, long ttl, String record) throws IOException {
+	newUpdate(Record.fromString(name, type, dclass, ttl, record, origin));
+}
+
+/**
+ * Parses a record from the tokenizer, and indicates that the record
+ * should be inserted into the zone.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+add(Name name, int type, long ttl, Tokenizer tokenizer) throws IOException {
+	newUpdate(Record.fromString(name, type, dclass, ttl, tokenizer,
+				    origin));
+}
+
+/**
+ * Indicates that the record should be inserted into the zone.
+ */
+public void
+add(Record record) {
+	newUpdate(record);
+}
+
+/**
+ * Indicates that the records should be inserted into the zone.
+ */
+public void
+add(Record [] records) {
+	for (int i = 0; i < records.length; i++)
+		add(records[i]);
+}
+
+/**
+ * Indicates that all of the records in the rrset should be inserted into the
+ * zone.
+ */
+public void
+add(RRset rrset) {
+	for (Iterator it = rrset.rrs(); it.hasNext(); )
+		add((Record) it.next());
+}
+
+/**
+ * Indicates that all records with the given name should be deleted from
+ * the zone.
+ */
+public void
+delete(Name name) {
+	newUpdate(Record.newRecord(name, Type.ANY, DClass.ANY, 0));
+}
+
+/**
+ * Indicates that all records with the given name and type should be deleted
+ * from the zone.
+ */
+public void
+delete(Name name, int type) {
+	newUpdate(Record.newRecord(name, type, DClass.ANY, 0));
+}
+
+/**
+ * Parses a record from the string, and indicates that the record
+ * should be deleted from the zone.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+delete(Name name, int type, String record) throws IOException {
+	newUpdate(Record.fromString(name, type, DClass.NONE, 0, record,
+				    origin));
+}
+
+/**
+ * Parses a record from the tokenizer, and indicates that the record
+ * should be deleted from the zone.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+delete(Name name, int type, Tokenizer tokenizer) throws IOException {
+	newUpdate(Record.fromString(name, type, DClass.NONE, 0, tokenizer,
+				    origin));
+}
+
+/**
+ * Indicates that the specified record should be deleted from the zone.
+ */
+public void
+delete(Record record) {
+	newUpdate(record.withDClass(DClass.NONE, 0));
+}
+
+/**
+ * Indicates that the records should be deleted from the zone.
+ */
+public void
+delete(Record [] records) {
+	for (int i = 0; i < records.length; i++)
+		delete(records[i]);
+}
+
+/**
+ * Indicates that all of the records in the rrset should be deleted from the
+ * zone.
+ */
+public void
+delete(RRset rrset) {
+	for (Iterator it = rrset.rrs(); it.hasNext(); )
+		delete((Record) it.next());
+}
+
+/**
+ * Parses a record from the string, and indicates that the record
+ * should be inserted into the zone replacing any other records with the
+ * same name and type.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+replace(Name name, int type, long ttl, String record) throws IOException {
+	delete(name, type);
+	add(name, type, ttl, record);
+}
+
+/**
+ * Parses a record from the tokenizer, and indicates that the record
+ * should be inserted into the zone replacing any other records with the
+ * same name and type.
+ * @throws IOException The record could not be parsed.
+ */
+public void
+replace(Name name, int type, long ttl, Tokenizer tokenizer) throws IOException
+{
+	delete(name, type);
+	add(name, type, ttl, tokenizer);
+}
+
+/**
+ * Indicates that the record should be inserted into the zone replacing any
+ * other records with the same name and type.
+ */
+public void
+replace(Record record) {
+	delete(record.getName(), record.getType());
+	add(record);
+}
+
+/**
+ * Indicates that the records should be inserted into the zone replacing any
+ * other records with the same name and type as each one.
+ */
+public void
+replace(Record [] records) {
+	for (int i = 0; i < records.length; i++)
+		replace(records[i]);
+}
+
+/**
+ * Indicates that all of the records in the rrset should be inserted into the
+ * zone replacing any other records with the same name and type.
+ */
+public void
+replace(RRset rrset) {
+	delete(rrset.getName(), rrset.getType());
+	for (Iterator it = rrset.rrs(); it.hasNext(); )
+		add((Record) it.next());
+}
+
+}
diff --git a/src/org/xbill/DNS/WKSRecord.java b/src/org/xbill/DNS/WKSRecord.java
new file mode 100644
index 0000000..10b61be
--- /dev/null
+++ b/src/org/xbill/DNS/WKSRecord.java
@@ -0,0 +1,719 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.net.*;
+import java.io.*;
+import java.util.*;
+
+/**
+ * Well Known Services - Lists services offered by this host.
+ *
+ * @author Brian Wellington
+ */
+
+public class WKSRecord extends Record {
+
+private static final long serialVersionUID = -9104259763909119805L;
+
+public static class Protocol {
+	/**
+	 * IP protocol identifiers.  This is basically copied out of RFC 1010.
+	 */
+
+	private Protocol() {}
+
+	/** Internet Control Message */
+	public static final int ICMP = 1;
+
+	/** Internet Group Management */
+	public static final int IGMP = 2;
+
+	/** Gateway-to-Gateway */
+	public static final int GGP = 3;
+
+	/** Stream */
+	public static final int ST = 5;
+
+	/** Transmission Control */
+	public static final int TCP = 6;
+
+	/** UCL */
+	public static final int UCL = 7;
+
+	/** Exterior Gateway Protocol */
+	public static final int EGP = 8;
+
+	/** any private interior gateway */
+	public static final int IGP = 9;
+
+	/** BBN RCC Monitoring */
+	public static final int BBN_RCC_MON = 10;
+
+	/** Network Voice Protocol */
+	public static final int NVP_II = 11;
+
+	/** PUP */
+	public static final int PUP = 12;
+
+	/** ARGUS */
+	public static final int ARGUS = 13;
+
+	/** EMCON */
+	public static final int EMCON = 14;
+
+	/** Cross Net Debugger */
+	public static final int XNET = 15;
+
+	/** Chaos */
+	public static final int CHAOS = 16;
+
+	/** User Datagram */
+	public static final int UDP = 17;
+
+	/** Multiplexing */
+	public static final int MUX = 18;
+
+	/** DCN Measurement Subsystems */
+	public static final int DCN_MEAS = 19;
+
+	/** Host Monitoring */
+	public static final int HMP = 20;
+
+	/** Packet Radio Measurement */
+	public static final int PRM = 21;
+
+	/** XEROX NS IDP */
+	public static final int XNS_IDP = 22;
+
+	/** Trunk-1 */
+	public static final int TRUNK_1 = 23;
+
+	/** Trunk-2 */
+	public static final int TRUNK_2 = 24;
+
+	/** Leaf-1 */
+	public static final int LEAF_1 = 25;
+
+	/** Leaf-2 */
+	public static final int LEAF_2 = 26;
+
+	/** Reliable Data Protocol */
+	public static final int RDP = 27;
+
+	/** Internet Reliable Transaction */
+	public static final int IRTP = 28;
+
+	/** ISO Transport Protocol Class 4 */
+	public static final int ISO_TP4 = 29;
+
+	/** Bulk Data Transfer Protocol */
+	public static final int NETBLT = 30;
+
+	/** MFE Network Services Protocol */
+	public static final int MFE_NSP = 31;
+
+	/** MERIT Internodal Protocol */
+	public static final int MERIT_INP = 32;
+
+	/** Sequential Exchange Protocol */
+	public static final int SEP = 33;
+
+	/** CFTP */
+	public static final int CFTP = 62;
+
+	/** SATNET and Backroom EXPAK */
+	public static final int SAT_EXPAK = 64;
+
+	/** MIT Subnet Support */
+	public static final int MIT_SUBNET = 65;
+
+	/** MIT Remote Virtual Disk Protocol */
+	public static final int RVD = 66;
+
+	/** Internet Pluribus Packet Core */
+	public static final int IPPC = 67;
+
+	/** SATNET Monitoring */
+	public static final int SAT_MON = 69;
+
+	/** Internet Packet Core Utility */
+	public static final int IPCV = 71;
+
+	/** Backroom SATNET Monitoring */
+	public static final int BR_SAT_MON = 76;
+
+	/** WIDEBAND Monitoring */
+	public static final int WB_MON = 78;
+
+	/** WIDEBAND EXPAK */
+	public static final int WB_EXPAK = 79;
+
+	private static Mnemonic protocols = new Mnemonic("IP protocol",
+							 Mnemonic.CASE_LOWER);
+
+	static {
+		protocols.setMaximum(0xFF);
+		protocols.setNumericAllowed(true);
+
+		protocols.add(ICMP, "icmp");
+		protocols.add(IGMP, "igmp");
+		protocols.add(GGP, "ggp");
+		protocols.add(ST, "st");
+		protocols.add(TCP, "tcp");
+		protocols.add(UCL, "ucl");
+		protocols.add(EGP, "egp");
+		protocols.add(IGP, "igp");
+		protocols.add(BBN_RCC_MON, "bbn-rcc-mon");
+		protocols.add(NVP_II, "nvp-ii");
+		protocols.add(PUP, "pup");
+		protocols.add(ARGUS, "argus");
+		protocols.add(EMCON, "emcon");
+		protocols.add(XNET, "xnet");
+		protocols.add(CHAOS, "chaos");
+		protocols.add(UDP, "udp");
+		protocols.add(MUX, "mux");
+		protocols.add(DCN_MEAS, "dcn-meas");
+		protocols.add(HMP, "hmp");
+		protocols.add(PRM, "prm");
+		protocols.add(XNS_IDP, "xns-idp");
+		protocols.add(TRUNK_1, "trunk-1");
+		protocols.add(TRUNK_2, "trunk-2");
+		protocols.add(LEAF_1, "leaf-1");
+		protocols.add(LEAF_2, "leaf-2");
+		protocols.add(RDP, "rdp");
+		protocols.add(IRTP, "irtp");
+		protocols.add(ISO_TP4, "iso-tp4");
+		protocols.add(NETBLT, "netblt");
+		protocols.add(MFE_NSP, "mfe-nsp");
+		protocols.add(MERIT_INP, "merit-inp");
+		protocols.add(SEP, "sep");
+		protocols.add(CFTP, "cftp");
+		protocols.add(SAT_EXPAK, "sat-expak");
+		protocols.add(MIT_SUBNET, "mit-subnet");
+		protocols.add(RVD, "rvd");
+		protocols.add(IPPC, "ippc");
+		protocols.add(SAT_MON, "sat-mon");
+		protocols.add(IPCV, "ipcv");
+		protocols.add(BR_SAT_MON, "br-sat-mon");
+		protocols.add(WB_MON, "wb-mon");
+		protocols.add(WB_EXPAK, "wb-expak");
+	}
+
+	/**
+	 * Converts an IP protocol value into its textual representation
+	 */
+	public static String
+	string(int type) {
+		return protocols.getText(type);
+	}
+
+	/**
+	 * Converts a textual representation of an IP protocol into its
+	 * numeric code.  Integers in the range 0..255 are also accepted.
+	 * @param s The textual representation of the protocol
+	 * @return The protocol code, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return protocols.getValue(s);
+	}
+}
+
+public static class Service {
+	/**
+	 * TCP/UDP services.  This is basically copied out of RFC 1010,
+	 * with MIT-ML-DEV removed, as it is not unique, and the description
+	 * of SWIFT-RVF fixed.
+	 */
+
+	private Service() {}
+
+	/** Remote Job Entry */
+	public static final int RJE = 5;
+
+	/** Echo */
+	public static final int ECHO = 7;
+
+	/** Discard */
+	public static final int DISCARD = 9;
+
+	/** Active Users */
+	public static final int USERS = 11;
+
+	/** Daytime */
+	public static final int DAYTIME = 13;
+
+	/** Quote of the Day */
+	public static final int QUOTE = 17;
+
+	/** Character Generator */
+	public static final int CHARGEN = 19;
+
+	/** File Transfer [Default Data] */
+	public static final int FTP_DATA = 20;
+
+	/** File Transfer [Control] */
+	public static final int FTP = 21;
+
+	/** Telnet */
+	public static final int TELNET = 23;
+
+	/** Simple Mail Transfer */
+	public static final int SMTP = 25;
+
+	/** NSW User System FE */
+	public static final int NSW_FE = 27;
+
+	/** MSG ICP */
+	public static final int MSG_ICP = 29;
+
+	/** MSG Authentication */
+	public static final int MSG_AUTH = 31;
+
+	/** Display Support Protocol */
+	public static final int DSP = 33;
+
+	/** Time */
+	public static final int TIME = 37;
+
+	/** Resource Location Protocol */
+	public static final int RLP = 39;
+
+	/** Graphics */
+	public static final int GRAPHICS = 41;
+
+	/** Host Name Server */
+	public static final int NAMESERVER = 42;
+
+	/** Who Is */
+	public static final int NICNAME = 43;
+
+	/** MPM FLAGS Protocol */
+	public static final int MPM_FLAGS = 44;
+
+	/** Message Processing Module [recv] */
+	public static final int MPM = 45;
+
+	/** MPM [default send] */
+	public static final int MPM_SND = 46;
+
+	/** NI FTP */
+	public static final int NI_FTP = 47;
+
+	/** Login Host Protocol */
+	public static final int LOGIN = 49;
+
+	/** IMP Logical Address Maintenance */
+	public static final int LA_MAINT = 51;
+
+	/** Domain Name Server */
+	public static final int DOMAIN = 53;
+
+	/** ISI Graphics Language */
+	public static final int ISI_GL = 55;
+
+	/** NI MAIL */
+	public static final int NI_MAIL = 61;
+
+	/** VIA Systems - FTP */
+	public static final int VIA_FTP = 63;
+
+	/** TACACS-Database Service */
+	public static final int TACACS_DS = 65;
+
+	/** Bootstrap Protocol Server */
+	public static final int BOOTPS = 67;
+
+	/** Bootstrap Protocol Client */
+	public static final int BOOTPC = 68;
+
+	/** Trivial File Transfer */
+	public static final int TFTP = 69;
+
+	/** Remote Job Service */
+	public static final int NETRJS_1 = 71;
+
+	/** Remote Job Service */
+	public static final int NETRJS_2 = 72;
+
+	/** Remote Job Service */
+	public static final int NETRJS_3 = 73;
+
+	/** Remote Job Service */
+	public static final int NETRJS_4 = 74;
+
+	/** Finger */
+	public static final int FINGER = 79;
+
+	/** HOSTS2 Name Server */
+	public static final int HOSTS2_NS = 81;
+
+	/** SU/MIT Telnet Gateway */
+	public static final int SU_MIT_TG = 89;
+
+	/** MIT Dover Spooler */
+	public static final int MIT_DOV = 91;
+
+	/** Device Control Protocol */
+	public static final int DCP = 93;
+
+	/** SUPDUP */
+	public static final int SUPDUP = 95;
+
+	/** Swift Remote Virtual File Protocol */
+	public static final int SWIFT_RVF = 97;
+
+	/** TAC News */
+	public static final int TACNEWS = 98;
+
+	/** Metagram Relay */
+	public static final int METAGRAM = 99;
+
+	/** NIC Host Name Server */
+	public static final int HOSTNAME = 101;
+
+	/** ISO-TSAP */
+	public static final int ISO_TSAP = 102;
+
+	/** X400 */
+	public static final int X400 = 103;
+
+	/** X400-SND */
+	public static final int X400_SND = 104;
+
+	/** Mailbox Name Nameserver */
+	public static final int CSNET_NS = 105;
+
+	/** Remote Telnet Service */
+	public static final int RTELNET = 107;
+
+	/** Post Office Protocol - Version 2 */
+	public static final int POP_2 = 109;
+
+	/** SUN Remote Procedure Call */
+	public static final int SUNRPC = 111;
+
+	/** Authentication Service */
+	public static final int AUTH = 113;
+
+	/** Simple File Transfer Protocol */
+	public static final int SFTP = 115;
+
+	/** UUCP Path Service */
+	public static final int UUCP_PATH = 117;
+
+	/** Network News Transfer Protocol */
+	public static final int NNTP = 119;
+
+	/** HYDRA Expedited Remote Procedure */
+	public static final int ERPC = 121;
+
+	/** Network Time Protocol */
+	public static final int NTP = 123;
+
+	/** Locus PC-Interface Net Map Server */
+	public static final int LOCUS_MAP = 125;
+
+	/** Locus PC-Interface Conn Server */
+	public static final int LOCUS_CON = 127;
+
+	/** Password Generator Protocol */
+	public static final int PWDGEN = 129;
+
+	/** CISCO FNATIVE */
+	public static final int CISCO_FNA = 130;
+
+	/** CISCO TNATIVE */
+	public static final int CISCO_TNA = 131;
+
+	/** CISCO SYSMAINT */
+	public static final int CISCO_SYS = 132;
+
+	/** Statistics Service */
+	public static final int STATSRV = 133;
+
+	/** INGRES-NET Service */
+	public static final int INGRES_NET = 134;
+
+	/** Location Service */
+	public static final int LOC_SRV = 135;
+
+	/** PROFILE Naming System */
+	public static final int PROFILE = 136;
+
+	/** NETBIOS Name Service */
+	public static final int NETBIOS_NS = 137;
+
+	/** NETBIOS Datagram Service */
+	public static final int NETBIOS_DGM = 138;
+
+	/** NETBIOS Session Service */
+	public static final int NETBIOS_SSN = 139;
+
+	/** EMFIS Data Service */
+	public static final int EMFIS_DATA = 140;
+
+	/** EMFIS Control Service */
+	public static final int EMFIS_CNTL = 141;
+
+	/** Britton-Lee IDM */
+	public static final int BL_IDM = 142;
+
+	/** Survey Measurement */
+	public static final int SUR_MEAS = 243;
+
+	/** LINK */
+	public static final int LINK = 245;
+
+	private static Mnemonic services = new Mnemonic("TCP/UDP service",
+							Mnemonic.CASE_LOWER);
+
+	static {
+		services.setMaximum(0xFFFF);
+		services.setNumericAllowed(true);
+
+		services.add(RJE, "rje");
+		services.add(ECHO, "echo");
+		services.add(DISCARD, "discard");
+		services.add(USERS, "users");
+		services.add(DAYTIME, "daytime");
+		services.add(QUOTE, "quote");
+		services.add(CHARGEN, "chargen");
+		services.add(FTP_DATA, "ftp-data");
+		services.add(FTP, "ftp");
+		services.add(TELNET, "telnet");
+		services.add(SMTP, "smtp");
+		services.add(NSW_FE, "nsw-fe");
+		services.add(MSG_ICP, "msg-icp");
+		services.add(MSG_AUTH, "msg-auth");
+		services.add(DSP, "dsp");
+		services.add(TIME, "time");
+		services.add(RLP, "rlp");
+		services.add(GRAPHICS, "graphics");
+		services.add(NAMESERVER, "nameserver");
+		services.add(NICNAME, "nicname");
+		services.add(MPM_FLAGS, "mpm-flags");
+		services.add(MPM, "mpm");
+		services.add(MPM_SND, "mpm-snd");
+		services.add(NI_FTP, "ni-ftp");
+		services.add(LOGIN, "login");
+		services.add(LA_MAINT, "la-maint");
+		services.add(DOMAIN, "domain");
+		services.add(ISI_GL, "isi-gl");
+		services.add(NI_MAIL, "ni-mail");
+		services.add(VIA_FTP, "via-ftp");
+		services.add(TACACS_DS, "tacacs-ds");
+		services.add(BOOTPS, "bootps");
+		services.add(BOOTPC, "bootpc");
+		services.add(TFTP, "tftp");
+		services.add(NETRJS_1, "netrjs-1");
+		services.add(NETRJS_2, "netrjs-2");
+		services.add(NETRJS_3, "netrjs-3");
+		services.add(NETRJS_4, "netrjs-4");
+		services.add(FINGER, "finger");
+		services.add(HOSTS2_NS, "hosts2-ns");
+		services.add(SU_MIT_TG, "su-mit-tg");
+		services.add(MIT_DOV, "mit-dov");
+		services.add(DCP, "dcp");
+		services.add(SUPDUP, "supdup");
+		services.add(SWIFT_RVF, "swift-rvf");
+		services.add(TACNEWS, "tacnews");
+		services.add(METAGRAM, "metagram");
+		services.add(HOSTNAME, "hostname");
+		services.add(ISO_TSAP, "iso-tsap");
+		services.add(X400, "x400");
+		services.add(X400_SND, "x400-snd");
+		services.add(CSNET_NS, "csnet-ns");
+		services.add(RTELNET, "rtelnet");
+		services.add(POP_2, "pop-2");
+		services.add(SUNRPC, "sunrpc");
+		services.add(AUTH, "auth");
+		services.add(SFTP, "sftp");
+		services.add(UUCP_PATH, "uucp-path");
+		services.add(NNTP, "nntp");
+		services.add(ERPC, "erpc");
+		services.add(NTP, "ntp");
+		services.add(LOCUS_MAP, "locus-map");
+		services.add(LOCUS_CON, "locus-con");
+		services.add(PWDGEN, "pwdgen");
+		services.add(CISCO_FNA, "cisco-fna");
+		services.add(CISCO_TNA, "cisco-tna");
+		services.add(CISCO_SYS, "cisco-sys");
+		services.add(STATSRV, "statsrv");
+		services.add(INGRES_NET, "ingres-net");
+		services.add(LOC_SRV, "loc-srv");
+		services.add(PROFILE, "profile");
+		services.add(NETBIOS_NS, "netbios-ns");
+		services.add(NETBIOS_DGM, "netbios-dgm");
+		services.add(NETBIOS_SSN, "netbios-ssn");
+		services.add(EMFIS_DATA, "emfis-data");
+		services.add(EMFIS_CNTL, "emfis-cntl");
+		services.add(BL_IDM, "bl-idm");
+		services.add(SUR_MEAS, "sur-meas");
+		services.add(LINK, "link");
+	}
+
+	/**
+	 * Converts a TCP/UDP service port number into its textual
+	 * representation.
+	 */
+	public static String
+	string(int type) {
+		return services.getText(type);
+	}
+
+	/**
+	 * Converts a textual representation of a TCP/UDP service into its
+	 * port number.  Integers in the range 0..65535 are also accepted.
+	 * @param s The textual representation of the service.
+	 * @return The port number, or -1 on error.
+	 */
+	public static int
+	value(String s) {
+		return services.getValue(s);
+	}
+}
+private byte [] address;
+private int protocol;
+private int [] services;
+
+WKSRecord() {}
+
+Record
+getObject() {
+	return new WKSRecord();
+}
+
+/**
+ * Creates a WKS Record from the given data
+ * @param address The IP address
+ * @param protocol The IP protocol number
+ * @param services An array of supported services, represented by port number.
+ */
+public
+WKSRecord(Name name, int dclass, long ttl, InetAddress address, int protocol,
+	  int [] services)
+{
+	super(name, Type.WKS, dclass, ttl);
+	if (Address.familyOf(address) != Address.IPv4)
+		throw new IllegalArgumentException("invalid IPv4 address");
+	this.address = address.getAddress();
+	this.protocol = checkU8("protocol", protocol);
+	for (int i = 0; i < services.length; i++) {
+		checkU16("service", services[i]);
+	}
+	this.services = new int[services.length];
+	System.arraycopy(services, 0, this.services, 0, services.length);
+	Arrays.sort(this.services);
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	address = in.readByteArray(4);
+	protocol = in.readU8();
+	byte [] array = in.readByteArray();
+	List list = new ArrayList();
+	for (int i = 0; i < array.length; i++) {
+		for (int j = 0; j < 8; j++) {
+			int octet = array[i] & 0xFF;
+			if ((octet & (1 << (7 - j))) != 0) {
+				list.add(new Integer(i * 8 + j));
+			}
+		}
+	}
+	services = new int[list.size()];
+	for (int i = 0; i < list.size(); i++) {
+		services[i] = ((Integer) list.get(i)).intValue();
+	}
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String s = st.getString();
+	address = Address.toByteArray(s, Address.IPv4);
+	if (address == null)
+		throw st.exception("invalid address");
+
+	s = st.getString();
+	protocol = Protocol.value(s);
+	if (protocol < 0) {
+		throw st.exception("Invalid IP protocol: " + s);
+	}
+
+	List list = new ArrayList();
+	while (true) {
+		Tokenizer.Token t = st.get();
+		if (!t.isString())
+			break;
+		int service = Service.value(t.value);
+		if (service < 0) {
+			throw st.exception("Invalid TCP/UDP service: " +
+					   t.value);
+		}
+		list.add(new Integer(service));
+	}
+	st.unget();
+	services = new int[list.size()];
+	for (int i = 0; i < list.size(); i++) {
+		services[i] = ((Integer) list.get(i)).intValue();
+	}
+}
+
+/**
+ * Converts rdata to a String
+ */
+String
+rrToString() {
+	StringBuffer sb = new StringBuffer();
+	sb.append(Address.toDottedQuad(address));
+	sb.append(" ");
+	sb.append(protocol);
+	for (int i = 0; i < services.length; i++) {
+		sb.append(" " + services[i]);
+	}
+	return sb.toString();
+}
+
+/**
+ * Returns the IP address.
+ */
+public InetAddress
+getAddress() {
+	try {
+		return InetAddress.getByAddress(address);
+	} catch (UnknownHostException e) {
+		return null;
+	}
+}
+
+/**
+ * Returns the IP protocol.
+ */
+public int
+getProtocol() {
+	return protocol;
+}
+
+/**
+ * Returns the services provided by the host on the specified address.
+ */
+public int []
+getServices() {
+	return services;
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeByteArray(address);
+	out.writeU8(protocol);
+	int highestPort = services[services.length - 1];
+	byte [] array = new byte[highestPort / 8 + 1];
+	for (int i = 0; i < services.length; i++) {
+		int port = services[i];
+		array[port / 8] |= (1 << (7 - port % 8));
+	}
+	out.writeByteArray(array);
+}
+
+}
diff --git a/src/org/xbill/DNS/WireParseException.java b/src/org/xbill/DNS/WireParseException.java
new file mode 100644
index 0000000..2842731
--- /dev/null
+++ b/src/org/xbill/DNS/WireParseException.java
@@ -0,0 +1,31 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * An exception thrown when a DNS message is invalid.
+ *
+ * @author Brian Wellington
+ */
+
+public class WireParseException extends IOException {
+
+public
+WireParseException() {
+	super();
+}
+
+public
+WireParseException(String s) {
+	super(s);
+}
+
+public
+WireParseException(String s, Throwable cause) {
+	super(s);
+	initCause(cause);
+}
+
+}
diff --git a/src/org/xbill/DNS/X25Record.java b/src/org/xbill/DNS/X25Record.java
new file mode 100644
index 0000000..1349a1e
--- /dev/null
+++ b/src/org/xbill/DNS/X25Record.java
@@ -0,0 +1,86 @@
+// Copyright (c) 2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+
+/**
+ * X25 - identifies the PSDN (Public Switched Data Network) address in the
+ * X.121 numbering plan associated with a name.
+ *
+ * @author Brian Wellington
+ */
+
+public class X25Record extends Record {
+
+private static final long serialVersionUID = 4267576252335579764L;
+
+private byte [] address;
+
+X25Record() {}
+
+Record
+getObject() {
+	return new X25Record();
+}
+
+private static final byte []
+checkAndConvertAddress(String address) {
+	int length = address.length();
+	byte [] out = new byte [length];
+	for (int i = 0; i < length; i++) {
+		char c = address.charAt(i);
+		if (!Character.isDigit(c))
+			return null;
+		out[i] = (byte) c;
+	}
+	return out;
+}
+
+/**
+ * Creates an X25 Record from the given data
+ * @param address The X.25 PSDN address.
+ * @throws IllegalArgumentException The address is not a valid PSDN address.
+ */
+public
+X25Record(Name name, int dclass, long ttl, String address) {
+	super(name, Type.X25, dclass, ttl);
+	this.address = checkAndConvertAddress(address);
+	if (this.address == null) {
+		throw new IllegalArgumentException("invalid PSDN address " +
+						   address);
+	}
+}
+
+void
+rrFromWire(DNSInput in) throws IOException {
+	address = in.readCountedString();
+}
+
+void
+rdataFromString(Tokenizer st, Name origin) throws IOException {
+	String addr = st.getString();
+	this.address = checkAndConvertAddress(addr);
+	if (this.address == null)
+		throw st.exception("invalid PSDN address " + addr);
+}
+
+/**
+ * Returns the X.25 PSDN address.
+ */
+public String
+getAddress() {
+	return byteArrayToString(address, false);
+}
+
+void
+rrToWire(DNSOutput out, Compression c, boolean canonical) {
+	out.writeCountedString(address);
+}
+
+String
+rrToString() {
+	return byteArrayToString(address, true);
+}
+
+}
diff --git a/src/org/xbill/DNS/Zone.java b/src/org/xbill/DNS/Zone.java
new file mode 100644
index 0000000..866be77
--- /dev/null
+++ b/src/org/xbill/DNS/Zone.java
@@ -0,0 +1,559 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.util.*;
+
+/**
+ * A DNS Zone.  This encapsulates all data related to a Zone, and provides
+ * convenient lookup methods.
+ *
+ * @author Brian Wellington
+ */
+
+public class Zone implements Serializable {
+
+private static final long serialVersionUID = -9220510891189510942L;
+
+/** A primary zone */
+public static final int PRIMARY = 1;
+
+/** A secondary zone */
+public static final int SECONDARY = 2;
+
+private Map data;
+private Name origin;
+private Object originNode;
+private int dclass = DClass.IN;
+private RRset NS;
+private SOARecord SOA;
+private boolean hasWild;
+
+class ZoneIterator implements Iterator {
+	private Iterator zentries;
+	private RRset [] current;
+	private int count;
+	private boolean wantLastSOA;
+
+	ZoneIterator(boolean axfr) {
+		synchronized (Zone.this) {
+			zentries = data.entrySet().iterator();
+		}
+		wantLastSOA = axfr;
+		RRset [] sets = allRRsets(originNode);
+		current = new RRset[sets.length];
+		for (int i = 0, j = 2; i < sets.length; i++) {
+			int type = sets[i].getType();
+			if (type == Type.SOA)
+				current[0] = sets[i];
+			else if (type == Type.NS)
+				current[1] = sets[i];
+			else
+				current[j++] = sets[i];
+		}
+	}
+
+	public boolean
+	hasNext() {
+		return (current != null || wantLastSOA);
+	}
+
+	public Object
+	next() {
+		if (!hasNext()) {
+			throw new NoSuchElementException();
+		}
+		if (current == null) {
+			wantLastSOA = false;
+			return oneRRset(originNode, Type.SOA);
+		}
+		Object set = current[count++];
+		if (count == current.length) {
+			current = null;
+			while (zentries.hasNext()) {
+				Map.Entry entry = (Map.Entry) zentries.next();
+				if (entry.getKey().equals(origin))
+					continue;
+				RRset [] sets = allRRsets(entry.getValue());
+				if (sets.length == 0)
+					continue;
+				current = sets;
+				count = 0;
+				break;
+			}
+		}
+		return set;
+	}
+
+	public void
+	remove() {
+		throw new UnsupportedOperationException();
+	}
+}
+
+private void
+validate() throws IOException {
+	originNode = exactName(origin);
+	if (originNode == null)
+		throw new IOException(origin + ": no data specified");
+
+	RRset rrset = oneRRset(originNode, Type.SOA);
+	if (rrset == null || rrset.size() != 1)
+		throw new IOException(origin +
+				      ": exactly 1 SOA must be specified");
+	Iterator it = rrset.rrs();
+	SOA = (SOARecord) it.next();
+
+	NS = oneRRset(originNode, Type.NS);
+	if (NS == null)
+		throw new IOException(origin + ": no NS set specified");
+}
+
+private final void
+maybeAddRecord(Record record) throws IOException {
+	int rtype = record.getType();
+	Name name = record.getName();
+
+	if (rtype == Type.SOA && !name.equals(origin)) {
+		throw new IOException("SOA owner " + name +
+				      " does not match zone origin " +
+				      origin);
+	}
+	if (name.subdomain(origin))
+		addRecord(record);
+}
+
+/**
+ * Creates a Zone from the records in the specified master file.
+ * @param zone The name of the zone.
+ * @param file The master file to read from.
+ * @see Master
+ */
+public
+Zone(Name zone, String file) throws IOException {
+	data = new TreeMap();
+
+	if (zone == null)
+		throw new IllegalArgumentException("no zone name specified");
+	Master m = new Master(file, zone);
+	Record record;
+
+	origin = zone;
+	while ((record = m.nextRecord()) != null)
+		maybeAddRecord(record);
+	validate();
+}
+
+/**
+ * Creates a Zone from an array of records.
+ * @param zone The name of the zone.
+ * @param records The records to add to the zone.
+ * @see Master
+ */
+public
+Zone(Name zone, Record [] records) throws IOException {
+	data = new TreeMap();
+
+	if (zone == null)
+		throw new IllegalArgumentException("no zone name specified");
+	origin = zone;
+	for (int i = 0; i < records.length; i++)
+		maybeAddRecord(records[i]);
+	validate();
+}
+
+private void
+fromXFR(ZoneTransferIn xfrin) throws IOException, ZoneTransferException {
+	data = new TreeMap();
+
+	origin = xfrin.getName();
+	List records = xfrin.run();
+	for (Iterator it = records.iterator(); it.hasNext(); ) {
+		Record record = (Record) it.next();
+		maybeAddRecord(record);
+	}
+	if (!xfrin.isAXFR())
+		throw new IllegalArgumentException("zones can only be " +
+						   "created from AXFRs");
+	validate();
+}
+
+/**
+ * Creates a Zone by doing the specified zone transfer.
+ * @param xfrin The incoming zone transfer to execute.
+ * @see ZoneTransferIn
+ */
+public
+Zone(ZoneTransferIn xfrin) throws IOException, ZoneTransferException {
+	fromXFR(xfrin);
+}
+
+/**
+ * Creates a Zone by performing a zone transfer to the specified host.
+ * @see ZoneTransferIn
+ */
+public
+Zone(Name zone, int dclass, String remote)
+throws IOException, ZoneTransferException
+{
+	ZoneTransferIn xfrin = ZoneTransferIn.newAXFR(zone, remote, null);
+	xfrin.setDClass(dclass);
+	fromXFR(xfrin);
+}
+
+/** Returns the Zone's origin */
+public Name
+getOrigin() {
+	return origin;
+}
+
+/** Returns the Zone origin's NS records */
+public RRset
+getNS() {
+	return NS;
+}
+
+/** Returns the Zone's SOA record */
+public SOARecord
+getSOA() {
+	return SOA;
+}
+
+/** Returns the Zone's class */
+public int
+getDClass() {
+	return dclass;
+}
+
+private synchronized Object
+exactName(Name name) {
+	return data.get(name);
+}
+
+private synchronized RRset []
+allRRsets(Object types) {
+	if (types instanceof List) {
+		List typelist = (List) types;
+		return (RRset []) typelist.toArray(new RRset[typelist.size()]);
+	} else {
+		RRset set = (RRset) types;
+		return new RRset [] {set};
+	}
+}
+
+private synchronized RRset
+oneRRset(Object types, int type) {
+	if (type == Type.ANY)
+		throw new IllegalArgumentException("oneRRset(ANY)");
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			RRset set = (RRset) list.get(i);
+			if (set.getType() == type)
+				return set;
+		}
+	} else {
+		RRset set = (RRset) types;
+		if (set.getType() == type)
+			return set;
+	}
+	return null;
+}
+
+private synchronized RRset
+findRRset(Name name, int type) {
+	Object types = exactName(name);
+	if (types == null)
+		return null;
+	return oneRRset(types, type);
+}
+
+private synchronized void
+addRRset(Name name, RRset rrset) {
+	if (!hasWild && name.isWild())
+		hasWild = true;
+	Object types = data.get(name);
+	if (types == null) {
+		data.put(name, rrset);
+		return;
+	}
+	int rtype = rrset.getType();
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			RRset set = (RRset) list.get(i);
+			if (set.getType() == rtype) {
+				list.set(i, rrset);
+				return;
+			}
+		}
+		list.add(rrset);
+	} else {
+		RRset set = (RRset) types;
+		if (set.getType() == rtype)
+			data.put(name, rrset);
+		else {
+			LinkedList list = new LinkedList();
+			list.add(set);
+			list.add(rrset);
+			data.put(name, list);
+		}
+	}
+}
+
+private synchronized void
+removeRRset(Name name, int type) {
+	Object types = data.get(name);
+	if (types == null) {
+		return;
+	}
+	if (types instanceof List) {
+		List list = (List) types;
+		for (int i = 0; i < list.size(); i++) {
+			RRset set = (RRset) list.get(i);
+			if (set.getType() == type) {
+				list.remove(i);
+				if (list.size() == 0)
+					data.remove(name);
+				return;
+			}
+		}
+	} else {
+		RRset set = (RRset) types;
+		if (set.getType() != type)
+			return;
+		data.remove(name);
+	}
+}
+
+private synchronized SetResponse
+lookup(Name name, int type) {
+	int labels;
+	int olabels;
+	int tlabels;
+	RRset rrset;
+	Name tname;
+	Object types;
+	SetResponse sr;
+
+	if (!name.subdomain(origin))
+		return SetResponse.ofType(SetResponse.NXDOMAIN);
+
+	labels = name.labels();
+	olabels = origin.labels();
+
+	for (tlabels = olabels; tlabels <= labels; tlabels++) {
+		boolean isOrigin = (tlabels == olabels);
+		boolean isExact = (tlabels == labels);
+
+		if (isOrigin)
+			tname = origin;
+		else if (isExact)
+			tname = name;
+		else
+			tname = new Name(name, labels - tlabels);
+
+		types = exactName(tname);
+		if (types == null)
+			continue;
+
+		/* If this is a delegation, return that. */
+		if (!isOrigin) {
+			RRset ns = oneRRset(types, Type.NS);
+			if (ns != null)
+				return new SetResponse(SetResponse.DELEGATION,
+						       ns);
+		}
+
+		/* If this is an ANY lookup, return everything. */
+		if (isExact && type == Type.ANY) {
+			sr = new SetResponse(SetResponse.SUCCESSFUL);
+			RRset [] sets = allRRsets(types);
+			for (int i = 0; i < sets.length; i++)
+				sr.addRRset(sets[i]);
+			return sr;
+		}
+
+		/*
+		 * If this is the name, look for the actual type or a CNAME.
+		 * Otherwise, look for a DNAME.
+		 */
+		if (isExact) {
+			rrset = oneRRset(types, type);
+			if (rrset != null) {
+				sr = new SetResponse(SetResponse.SUCCESSFUL);
+				sr.addRRset(rrset);
+				return sr;
+			}
+			rrset = oneRRset(types, Type.CNAME);
+			if (rrset != null)
+				return new SetResponse(SetResponse.CNAME,
+						       rrset);
+		} else {
+			rrset = oneRRset(types, Type.DNAME);
+			if (rrset != null)
+				return new SetResponse(SetResponse.DNAME,
+						       rrset);
+		}
+
+		/* We found the name, but not the type. */
+		if (isExact)
+			return SetResponse.ofType(SetResponse.NXRRSET);
+	}
+
+	if (hasWild) {
+		for (int i = 0; i < labels - olabels; i++) {
+			tname = name.wild(i + 1);
+
+			types = exactName(tname);
+			if (types == null)
+				continue;
+
+			rrset = oneRRset(types, type);
+			if (rrset != null) {
+				sr = new SetResponse(SetResponse.SUCCESSFUL);
+				sr.addRRset(rrset);
+				return sr;
+			}
+		}
+	}
+
+	return SetResponse.ofType(SetResponse.NXDOMAIN);
+}
+
+/**     
+ * Looks up Records in the Zone.  This follows CNAMEs and wildcards.
+ * @param name The name to look up
+ * @param type The type to look up
+ * @return A SetResponse object
+ * @see SetResponse
+ */ 
+public SetResponse
+findRecords(Name name, int type) {
+	return lookup(name, type);
+}
+
+/**
+ * Looks up Records in the zone, finding exact matches only.
+ * @param name The name to look up
+ * @param type The type to look up
+ * @return The matching RRset
+ * @see RRset
+ */ 
+public RRset
+findExactMatch(Name name, int type) {
+	Object types = exactName(name);
+	if (types == null)
+		return null;
+	return oneRRset(types, type);
+}
+
+/**
+ * Adds an RRset to the Zone
+ * @param rrset The RRset to be added
+ * @see RRset
+ */
+public void
+addRRset(RRset rrset) {
+	Name name = rrset.getName();
+	addRRset(name, rrset);
+}
+
+/**
+ * Adds a Record to the Zone
+ * @param r The record to be added
+ * @see Record
+ */
+public void
+addRecord(Record r) {
+	Name name = r.getName();
+	int rtype = r.getRRsetType();
+	synchronized (this) {
+		RRset rrset = findRRset(name, rtype);
+		if (rrset == null) {
+			rrset = new RRset(r);
+			addRRset(name, rrset);
+		} else {
+			rrset.addRR(r);
+		}
+	}
+}
+
+/**
+ * Removes a record from the Zone
+ * @param r The record to be removed
+ * @see Record
+ */
+public void
+removeRecord(Record r) {
+	Name name = r.getName();
+	int rtype = r.getRRsetType();
+	synchronized (this) {
+		RRset rrset = findRRset(name, rtype);
+		if (rrset == null)
+			return;
+		if (rrset.size() == 1 && rrset.first().equals(r))
+			removeRRset(name, rtype);
+		else
+			rrset.deleteRR(r);
+	}
+}
+
+/**
+ * Returns an Iterator over the RRsets in the zone.
+ */
+public Iterator
+iterator() {
+	return new ZoneIterator(false);
+}
+
+/**
+ * Returns an Iterator over the RRsets in the zone that can be used to
+ * construct an AXFR response.  This is identical to {@link #iterator} except
+ * that the SOA is returned at the end as well as the beginning.
+ */
+public Iterator
+AXFR() {
+	return new ZoneIterator(true);
+}
+
+private void
+nodeToString(StringBuffer sb, Object node) {
+	RRset [] sets = allRRsets(node);
+	for (int i = 0; i < sets.length; i++) {
+		RRset rrset = sets[i];
+		Iterator it = rrset.rrs();
+		while (it.hasNext())
+			sb.append(it.next() + "\n");
+		it = rrset.sigs();
+		while (it.hasNext())
+			sb.append(it.next() + "\n");
+	}
+}
+
+/**
+ * Returns the contents of the Zone in master file format.
+ */
+public synchronized String
+toMasterFile() {
+	Iterator zentries = data.entrySet().iterator();
+	StringBuffer sb = new StringBuffer();
+	nodeToString(sb, originNode);
+	while (zentries.hasNext()) {
+		Map.Entry entry = (Map.Entry) zentries.next();
+		if (!origin.equals(entry.getKey()))
+			nodeToString(sb, entry.getValue());
+	}
+	return sb.toString();
+}
+
+/**
+ * Returns the contents of the Zone as a string (in master file format).
+ */
+public String
+toString() {
+	return toMasterFile();
+}
+
+}
diff --git a/src/org/xbill/DNS/ZoneTransferException.java b/src/org/xbill/DNS/ZoneTransferException.java
new file mode 100644
index 0000000..3ba487b
--- /dev/null
+++ b/src/org/xbill/DNS/ZoneTransferException.java
@@ -0,0 +1,23 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS;
+
+/**
+ * An exception thrown when a zone transfer fails.
+ *
+ * @author Brian Wellington
+ */
+
+public class ZoneTransferException extends Exception {
+
+public
+ZoneTransferException() {
+	super();
+}
+
+public
+ZoneTransferException(String s) {
+	super(s);
+}
+
+}
diff --git a/src/org/xbill/DNS/ZoneTransferIn.java b/src/org/xbill/DNS/ZoneTransferIn.java
new file mode 100644
index 0000000..8a19992
--- /dev/null
+++ b/src/org/xbill/DNS/ZoneTransferIn.java
@@ -0,0 +1,680 @@
+// Copyright (c) 2003-2004 Brian Wellington (bwelling@xbill.org)
+// Parts of this are derived from lib/dns/xfrin.c from BIND 9; its copyright
+// notice follows.
+
+/*
+ * Copyright (C) 1999-2001  Internet Software Consortium.
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
+ * DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
+ * INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
+ * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
+ * FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
+ * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
+ * WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+package org.xbill.DNS;
+
+import java.io.*;
+import java.net.*;
+import java.util.*;
+
+/**
+ * An incoming DNS Zone Transfer.  To use this class, first initialize an
+ * object, then call the run() method.  If run() doesn't throw an exception
+ * the result will either be an IXFR-style response, an AXFR-style response,
+ * or an indication that the zone is up to date.
+ *
+ * @author Brian Wellington
+ */
+
+public class ZoneTransferIn {
+
+private static final int INITIALSOA	= 0;
+private static final int FIRSTDATA	= 1;
+private static final int IXFR_DELSOA	= 2;
+private static final int IXFR_DEL	= 3;
+private static final int IXFR_ADDSOA	= 4;
+private static final int IXFR_ADD	= 5;
+private static final int AXFR		= 6;
+private static final int END		= 7;
+
+private Name zname;
+private int qtype;
+private int dclass;
+private long ixfr_serial;
+private boolean want_fallback;
+private ZoneTransferHandler handler;
+
+private SocketAddress localAddress;
+private SocketAddress address;
+private TCPClient client;
+private TSIG tsig;
+private TSIG.StreamVerifier verifier;
+private long timeout = 900 * 1000;
+
+private int state;
+private long end_serial;
+private long current_serial;
+private Record initialsoa;
+
+private int rtype;
+
+public static class Delta {
+	/**
+	 * All changes between two versions of a zone in an IXFR response.
+	 */
+
+	/** The starting serial number of this delta. */
+	public long start;
+
+	/** The ending serial number of this delta. */
+	public long end;
+
+	/** A list of records added between the start and end versions */
+	public List adds;
+
+	/** A list of records deleted between the start and end versions */
+	public List deletes;
+
+	private
+	Delta() {
+		adds = new ArrayList();
+		deletes = new ArrayList();
+	}
+}
+
+public static interface ZoneTransferHandler {
+	/**
+	 * Handles a Zone Transfer.
+	 */
+
+	/**
+	 * Called when an AXFR transfer begins.
+	 */
+	public void startAXFR() throws ZoneTransferException;
+
+	/**
+	 * Called when an IXFR transfer begins.
+	 */
+	public void startIXFR() throws ZoneTransferException;
+
+	/**
+	 * Called when a series of IXFR deletions begins.
+	 * @param soa The starting SOA.
+	 */
+	public void startIXFRDeletes(Record soa) throws ZoneTransferException;
+
+	/**
+	 * Called when a series of IXFR adds begins.
+	 * @param soa The starting SOA.
+	 */
+	public void startIXFRAdds(Record soa) throws ZoneTransferException;
+
+	/**
+	 * Called for each content record in an AXFR.
+	 * @param r The DNS record.
+	 */
+	public void handleRecord(Record r) throws ZoneTransferException;
+};
+
+private static class BasicHandler implements ZoneTransferHandler {
+	private List axfr;
+	private List ixfr;
+
+	public void startAXFR() {
+		axfr = new ArrayList();
+	}
+
+	public void startIXFR() {
+		ixfr = new ArrayList();
+	}
+
+	public void startIXFRDeletes(Record soa) {
+		Delta delta = new Delta();
+		delta.deletes.add(soa);
+		delta.start = getSOASerial(soa);
+		ixfr.add(delta);
+	}
+
+	public void startIXFRAdds(Record soa) {
+		Delta delta = (Delta) ixfr.get(ixfr.size() - 1);
+		delta.adds.add(soa);
+		delta.end = getSOASerial(soa);
+	}
+
+	public void handleRecord(Record r) {
+		List list;
+		if (ixfr != null) {
+			Delta delta = (Delta) ixfr.get(ixfr.size() - 1);
+			if (delta.adds.size() > 0)
+				list = delta.adds;
+			else
+				list = delta.deletes;
+		} else
+			list = axfr;
+		list.add(r);
+	}
+};
+
+private
+ZoneTransferIn() {}
+
+private
+ZoneTransferIn(Name zone, int xfrtype, long serial, boolean fallback,
+	       SocketAddress address, TSIG key)
+{
+	this.address = address;
+	this.tsig = key;
+	if (zone.isAbsolute())
+		zname = zone;
+	else {
+		try {
+			zname = Name.concatenate(zone, Name.root);
+		}
+		catch (NameTooLongException e) {
+			throw new IllegalArgumentException("ZoneTransferIn: " +
+							   "name too long");
+		}
+	}
+	qtype = xfrtype;
+	dclass = DClass.IN;
+	ixfr_serial = serial;
+	want_fallback = fallback;
+	state = INITIALSOA;
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an AXFR (full zone transfer).
+ * @param zone The zone to transfer.
+ * @param address The host/port from which to transfer the zone.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newAXFR(Name zone, SocketAddress address, TSIG key) {
+	return new ZoneTransferIn(zone, Type.AXFR, 0, false, address, key);
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an AXFR (full zone transfer).
+ * @param zone The zone to transfer.
+ * @param host The host from which to transfer the zone.
+ * @param port The port to connect to on the server, or 0 for the default.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newAXFR(Name zone, String host, int port, TSIG key)
+throws UnknownHostException
+{
+	if (port == 0)
+		port = SimpleResolver.DEFAULT_PORT;
+	return newAXFR(zone, new InetSocketAddress(host, port), key);
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an AXFR (full zone transfer).
+ * @param zone The zone to transfer.
+ * @param host The host from which to transfer the zone.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newAXFR(Name zone, String host, TSIG key)
+throws UnknownHostException
+{
+	return newAXFR(zone, host, 0, key);
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an IXFR (incremental zone
+ * transfer).
+ * @param zone The zone to transfer.
+ * @param serial The existing serial number.
+ * @param fallback If true, fall back to AXFR if IXFR is not supported.
+ * @param address The host/port from which to transfer the zone.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newIXFR(Name zone, long serial, boolean fallback, SocketAddress address,
+	TSIG key)
+{
+	return new ZoneTransferIn(zone, Type.IXFR, serial, fallback, address,
+				  key);
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an IXFR (incremental zone
+ * transfer).
+ * @param zone The zone to transfer.
+ * @param serial The existing serial number.
+ * @param fallback If true, fall back to AXFR if IXFR is not supported.
+ * @param host The host from which to transfer the zone.
+ * @param port The port to connect to on the server, or 0 for the default.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newIXFR(Name zone, long serial, boolean fallback, String host, int port,
+	TSIG key)
+throws UnknownHostException
+{
+	if (port == 0)
+		port = SimpleResolver.DEFAULT_PORT;
+	return newIXFR(zone, serial, fallback,
+		       new InetSocketAddress(host, port), key);
+}
+
+/**
+ * Instantiates a ZoneTransferIn object to do an IXFR (incremental zone
+ * transfer).
+ * @param zone The zone to transfer.
+ * @param serial The existing serial number.
+ * @param fallback If true, fall back to AXFR if IXFR is not supported.
+ * @param host The host from which to transfer the zone.
+ * @param key The TSIG key used to authenticate the transfer, or null.
+ * @return The ZoneTransferIn object.
+ * @throws UnknownHostException The host does not exist.
+ */
+public static ZoneTransferIn
+newIXFR(Name zone, long serial, boolean fallback, String host, TSIG key)
+throws UnknownHostException
+{
+	return newIXFR(zone, serial, fallback, host, 0, key);
+}
+
+/**
+ * Gets the name of the zone being transferred.
+ */
+public Name
+getName() {
+	return zname;
+}
+
+/**
+ * Gets the type of zone transfer (either AXFR or IXFR).
+ */
+public int
+getType() {
+	return qtype;
+}
+
+/**
+ * Sets a timeout on this zone transfer.  The default is 900 seconds (15
+ * minutes).
+ * @param secs The maximum amount of time that this zone transfer can take.
+ */
+public void
+setTimeout(int secs) {
+	if (secs < 0)
+		throw new IllegalArgumentException("timeout cannot be " +
+						   "negative");
+	timeout = 1000L * secs;
+}
+
+/**
+ * Sets an alternate DNS class for this zone transfer.
+ * @param dclass The class to use instead of class IN.
+ */
+public void
+setDClass(int dclass) {
+	DClass.check(dclass);
+	this.dclass = dclass;
+}
+
+/**
+ * Sets the local address to bind to when sending messages.
+ * @param addr The local address to send messages from.
+ */
+public void
+setLocalAddress(SocketAddress addr) {
+	this.localAddress = addr;
+}
+
+private void
+openConnection() throws IOException {
+	long endTime = System.currentTimeMillis() + timeout;
+	client = new TCPClient(endTime);
+	if (localAddress != null)
+		client.bind(localAddress);
+	client.connect(address);
+}
+
+private void
+sendQuery() throws IOException {
+	Record question = Record.newRecord(zname, qtype, dclass);
+
+	Message query = new Message();
+	query.getHeader().setOpcode(Opcode.QUERY);
+	query.addRecord(question, Section.QUESTION);
+	if (qtype == Type.IXFR) {
+		Record soa = new SOARecord(zname, dclass, 0, Name.root,
+					   Name.root, ixfr_serial,
+					   0, 0, 0, 0);
+		query.addRecord(soa, Section.AUTHORITY);
+	}
+	if (tsig != null) {
+		tsig.apply(query, null);
+		verifier = new TSIG.StreamVerifier(tsig, query.getTSIG());
+	}
+	byte [] out = query.toWire(Message.MAXLENGTH);
+	client.send(out);
+}
+
+private static long
+getSOASerial(Record rec) {
+	SOARecord soa = (SOARecord) rec;
+	return soa.getSerial();
+}
+
+private void
+logxfr(String s) {
+	if (Options.check("verbose"))
+		System.out.println(zname + ": " + s);
+}
+
+private void
+fail(String s) throws ZoneTransferException {
+	throw new ZoneTransferException(s);
+}
+
+private void
+fallback() throws ZoneTransferException {
+	if (!want_fallback)
+		fail("server doesn't support IXFR");
+
+	logxfr("falling back to AXFR");
+	qtype = Type.AXFR;
+	state = INITIALSOA;
+}
+
+private void
+parseRR(Record rec) throws ZoneTransferException {
+	int type = rec.getType();
+	Delta delta;
+
+	switch (state) {
+	case INITIALSOA:
+		if (type != Type.SOA)
+			fail("missing initial SOA");
+		initialsoa = rec;
+		// Remember the serial number in the initial SOA; we need it
+		// to recognize the end of an IXFR.
+		end_serial = getSOASerial(rec);
+		if (qtype == Type.IXFR &&
+		    Serial.compare(end_serial, ixfr_serial) <= 0)
+		{
+			logxfr("up to date");
+			state = END;
+			break;
+		}
+		state = FIRSTDATA;
+		break;
+
+	case FIRSTDATA:
+		// If the transfer begins with 1 SOA, it's an AXFR.
+		// If it begins with 2 SOAs, it's an IXFR.
+		if (qtype == Type.IXFR && type == Type.SOA &&
+		    getSOASerial(rec) == ixfr_serial)
+		{
+			rtype = Type.IXFR;
+			handler.startIXFR();
+			logxfr("got incremental response");
+			state = IXFR_DELSOA;
+		} else {
+			rtype = Type.AXFR;
+			handler.startAXFR();
+			handler.handleRecord(initialsoa);
+			logxfr("got nonincremental response");
+			state = AXFR;
+		}
+		parseRR(rec); // Restart...
+		return;
+
+	case IXFR_DELSOA:
+		handler.startIXFRDeletes(rec);
+		state = IXFR_DEL;
+		break;
+
+	case IXFR_DEL:
+		if (type == Type.SOA) {
+			current_serial = getSOASerial(rec);
+			state = IXFR_ADDSOA;
+			parseRR(rec); // Restart...
+			return;
+		}
+		handler.handleRecord(rec);
+		break;
+
+	case IXFR_ADDSOA:
+		handler.startIXFRAdds(rec);
+		state = IXFR_ADD;
+		break;
+
+	case IXFR_ADD:
+		if (type == Type.SOA) {
+			long soa_serial = getSOASerial(rec);
+			if (soa_serial == end_serial) {
+				state = END;
+				break;
+			} else if (soa_serial != current_serial) {
+				fail("IXFR out of sync: expected serial " +
+				     current_serial + " , got " + soa_serial);
+			} else {
+				state = IXFR_DELSOA;
+				parseRR(rec); // Restart...
+				return;
+			}
+		}
+		handler.handleRecord(rec);
+		break;
+
+	case AXFR:
+		// Old BINDs sent cross class A records for non IN classes.
+		if (type == Type.A && rec.getDClass() != dclass)
+			break;
+		handler.handleRecord(rec);
+		if (type == Type.SOA) {
+			state = END;
+		}
+		break;
+
+	case END:
+		fail("extra data");
+		break;
+
+	default:
+		fail("invalid state");
+		break;
+	}
+}
+
+private void
+closeConnection() {
+	try {
+		if (client != null)
+			client.cleanup();
+	}
+	catch (IOException e) {
+	}
+}
+
+private Message
+parseMessage(byte [] b) throws WireParseException {
+	try {
+		return new Message(b);
+	}
+	catch (IOException e) {
+		if (e instanceof WireParseException)
+			throw (WireParseException) e;
+		throw new WireParseException("Error parsing message");
+	}
+}
+
+private void
+doxfr() throws IOException, ZoneTransferException {
+	sendQuery();
+	while (state != END) {
+		byte [] in = client.recv();
+		Message response =  parseMessage(in);
+		if (response.getHeader().getRcode() == Rcode.NOERROR &&
+		    verifier != null)
+		{
+			TSIGRecord tsigrec = response.getTSIG();
+
+			int error = verifier.verify(response, in);
+			if (error != Rcode.NOERROR)
+				fail("TSIG failure");
+		}
+
+		Record [] answers = response.getSectionArray(Section.ANSWER);
+
+		if (state == INITIALSOA) {
+			int rcode = response.getRcode();
+			if (rcode != Rcode.NOERROR) {
+				if (qtype == Type.IXFR &&
+				    rcode == Rcode.NOTIMP)
+				{
+					fallback();
+					doxfr();
+					return;
+				}
+				fail(Rcode.string(rcode));
+			}
+
+			Record question = response.getQuestion();
+			if (question != null && question.getType() != qtype) {
+				fail("invalid question section");
+			}
+
+			if (answers.length == 0 && qtype == Type.IXFR) {
+				fallback();
+				doxfr();
+				return;
+			}
+		}
+
+		for (int i = 0; i < answers.length; i++) {
+			parseRR(answers[i]);
+		}
+
+		if (state == END && verifier != null &&
+		    !response.isVerified())
+			fail("last message must be signed");
+	}
+}
+
+/**
+ * Does the zone transfer.
+ * @param handler The callback object that handles the zone transfer data.
+ * @throws IOException The zone transfer failed to due an IO problem.
+ * @throws ZoneTransferException The zone transfer failed to due a problem
+ * with the zone transfer itself.
+ */
+public void
+run(ZoneTransferHandler handler) throws IOException, ZoneTransferException {
+	this.handler = handler;
+	try {
+		openConnection();
+		doxfr();
+	}
+	finally {
+		closeConnection();
+	}
+}
+
+/**
+ * Does the zone transfer.
+ * @return A list, which is either an AXFR-style response (List of Records),
+ * and IXFR-style response (List of Deltas), or null, which indicates that
+ * an IXFR was performed and the zone is up to date.
+ * @throws IOException The zone transfer failed to due an IO problem.
+ * @throws ZoneTransferException The zone transfer failed to due a problem
+ * with the zone transfer itself.
+ */
+public List
+run() throws IOException, ZoneTransferException {
+	BasicHandler handler = new BasicHandler();
+	run(handler);
+	if (handler.axfr != null)
+		return handler.axfr;
+	return handler.ixfr;
+}
+
+private BasicHandler
+getBasicHandler() throws IllegalArgumentException {
+	if (handler instanceof BasicHandler)
+		return (BasicHandler) handler;
+	throw new IllegalArgumentException("ZoneTransferIn used callback " +
+					   "interface");
+}
+
+/**
+ * Returns true if the response is an AXFR-style response (List of Records).
+ * This will be true if either an IXFR was performed, an IXFR was performed
+ * and the server provided a full zone transfer, or an IXFR failed and
+ * fallback to AXFR occurred.
+ */
+public boolean
+isAXFR() {
+	return (rtype == Type.AXFR);
+}
+
+/**
+ * Gets the AXFR-style response.
+ * @throws IllegalArgumentException The transfer used the callback interface,
+ * so the response was not stored.
+ */
+public List
+getAXFR() {
+	BasicHandler handler = getBasicHandler();
+	return handler.axfr;
+}
+
+/**
+ * Returns true if the response is an IXFR-style response (List of Deltas).
+ * This will be true only if an IXFR was performed and the server provided
+ * an incremental zone transfer.
+ */
+public boolean
+isIXFR() {
+	return (rtype == Type.IXFR);
+}
+
+/**
+ * Gets the IXFR-style response.
+ * @throws IllegalArgumentException The transfer used the callback interface,
+ * so the response was not stored.
+ */
+public List
+getIXFR() {
+	BasicHandler handler = getBasicHandler();
+	return handler.ixfr;
+}
+
+/**
+ * Returns true if the response indicates that the zone is up to date.
+ * This will be true only if an IXFR was performed.
+ * @throws IllegalArgumentException The transfer used the callback interface,
+ * so the response was not stored.
+ */
+public boolean
+isCurrent() {
+	BasicHandler handler = getBasicHandler();
+	return (handler.axfr == null && handler.ixfr == null);
+}
+
+}
diff --git a/src/org/xbill/DNS/spi/DNSJavaNameService.java b/src/org/xbill/DNS/spi/DNSJavaNameService.java
new file mode 100644
index 0000000..14d8adb
--- /dev/null
+++ b/src/org/xbill/DNS/spi/DNSJavaNameService.java
@@ -0,0 +1,176 @@
+// Copyright (c) 2005 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.spi;
+
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.Method;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.util.StringTokenizer;
+
+import org.xbill.DNS.AAAARecord;
+import org.xbill.DNS.ARecord;
+import org.xbill.DNS.ExtendedResolver;
+import org.xbill.DNS.Lookup;
+import org.xbill.DNS.Name;
+import org.xbill.DNS.PTRRecord;
+import org.xbill.DNS.Record;
+import org.xbill.DNS.Resolver;
+import org.xbill.DNS.ReverseMap;
+import org.xbill.DNS.TextParseException;
+import org.xbill.DNS.Type;
+
+/**
+ * This class implements a Name Service Provider, which Java can use 
+ * (starting with version 1.4), to perform DNS resolutions instead of using 
+ * the standard calls. 
+ * <p>
+ * This Name Service Provider uses dnsjava.
+ * <p>
+ * To use this provider, you must set the following system property:
+ * <b>sun.net.spi.nameservice.provider.1=dns,dnsjava</b>
+ *
+ * @author Brian Wellington
+ * @author Paul Cowan (pwc21@yahoo.com)
+ */
+
+public class DNSJavaNameService implements InvocationHandler {
+
+private static final String nsProperty = "sun.net.spi.nameservice.nameservers";
+private static final String domainProperty = "sun.net.spi.nameservice.domain";
+private static final String v6Property = "java.net.preferIPv6Addresses";
+
+private boolean preferV6 = false;
+
+/**
+ * Creates a DNSJavaNameService instance.
+ * <p>
+ * Uses the
+ * <b>sun.net.spi.nameservice.nameservers</b>,
+ * <b>sun.net.spi.nameservice.domain</b>, and
+ * <b>java.net.preferIPv6Addresses</b> properties for configuration.
+ */
+protected
+DNSJavaNameService() {
+	String nameServers = System.getProperty(nsProperty);
+	String domain = System.getProperty(domainProperty);
+	String v6 = System.getProperty(v6Property);
+
+	if (nameServers != null) {
+		StringTokenizer st = new StringTokenizer(nameServers, ",");
+		String [] servers = new String[st.countTokens()];
+		int n = 0;
+		while (st.hasMoreTokens())
+			servers[n++] = st.nextToken();
+		try {
+			Resolver res = new ExtendedResolver(servers);
+			Lookup.setDefaultResolver(res);
+		}
+		catch (UnknownHostException e) {
+			System.err.println("DNSJavaNameService: invalid " +
+					   nsProperty);
+		}
+	}
+
+	if (domain != null) {
+		try {
+			Lookup.setDefaultSearchPath(new String[] {domain});
+		}
+		catch (TextParseException e) {
+			System.err.println("DNSJavaNameService: invalid " +
+					   domainProperty);
+		}
+	}
+
+	if (v6 != null && v6.equalsIgnoreCase("true"))
+		preferV6 = true;
+}
+
+
+public Object
+invoke(Object proxy, Method method, Object[] args) throws Throwable {
+	try {
+		if (method.getName().equals("getHostByAddr")) {
+			return this.getHostByAddr((byte[]) args[0]);
+		} else if (method.getName().equals("lookupAllHostAddr")) {
+			InetAddress[] addresses;
+			addresses = this.lookupAllHostAddr((String) args[0]);
+			Class returnType = method.getReturnType();
+			if (returnType.equals(InetAddress[].class)) {
+				// method for Java >= 1.6
+				return addresses;
+			} else if (returnType.equals(byte[][].class)) {
+				// method for Java <= 1.5
+				int naddrs = addresses.length;
+				byte [][] byteAddresses = new byte[naddrs][];
+				byte [] addr;
+				for (int i = 0; i < naddrs; i++) {
+					addr = addresses[i].getAddress();
+					byteAddresses[i] = addr;
+				}
+				return byteAddresses;
+			}
+		}		
+	} catch (Throwable e) {
+		System.err.println("DNSJavaNameService: Unexpected error.");
+		e.printStackTrace();
+		throw e;
+	}
+	throw new IllegalArgumentException(
+					"Unknown function name or arguments.");
+}
+
+/**
+ * Performs a forward DNS lookup for the host name.
+ * @param host The host name to resolve.
+ * @return All the ip addresses found for the host name.
+ */
+public InetAddress []
+lookupAllHostAddr(String host) throws UnknownHostException {
+	Name name = null;
+
+	try {
+		name = new Name(host);
+	}
+	catch (TextParseException e) {
+		throw new UnknownHostException(host);
+	}
+
+	Record [] records = null;
+	if (preferV6)
+		records = new Lookup(name, Type.AAAA).run();
+	if (records == null)
+		records = new Lookup(name, Type.A).run();
+	if (records == null && !preferV6)
+		records = new Lookup(name, Type.AAAA).run();
+	if (records == null)
+		throw new UnknownHostException(host);
+
+	InetAddress[] array = new InetAddress[records.length];
+	for (int i = 0; i < records.length; i++) {
+		Record record = records[i];
+		if (records[i] instanceof ARecord) {
+			ARecord a = (ARecord) records[i];
+			array[i] = a.getAddress();
+		} else {
+			AAAARecord aaaa = (AAAARecord) records[i];
+			array[i] = aaaa.getAddress();
+		}
+	}
+	return array;
+}
+
+/**
+ * Performs a reverse DNS lookup.
+ * @param addr The ip address to lookup.
+ * @return The host name found for the ip address.
+ */
+public String
+getHostByAddr(byte [] addr) throws UnknownHostException {
+	Name name = ReverseMap.fromAddress(InetAddress.getByAddress(addr));
+	Record [] records = new Lookup(name, Type.PTR).run();
+	if (records == null)
+		throw new UnknownHostException();
+	return ((PTRRecord) records[0]).getTarget().toString();
+}
+}
diff --git a/src/org/xbill/DNS/spi/services/sun.net.spi.nameservice.NameServiceDescriptor b/src/org/xbill/DNS/spi/services/sun.net.spi.nameservice.NameServiceDescriptor
new file mode 100644
index 0000000..1ca895c
--- /dev/null
+++ b/src/org/xbill/DNS/spi/services/sun.net.spi.nameservice.NameServiceDescriptor
@@ -0,0 +1 @@
+org.xbill.DNS.spi.DNSJavaNameServiceDescriptor
diff --git a/src/org/xbill/DNS/tests/primary.java b/src/org/xbill/DNS/tests/primary.java
new file mode 100644
index 0000000..85455b9
--- /dev/null
+++ b/src/org/xbill/DNS/tests/primary.java
@@ -0,0 +1,59 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.tests;
+
+import java.util.*;
+import org.xbill.DNS.*;
+
+public class primary {
+
+private static void
+usage() {
+	System.out.println("usage: primary [-t] [-a | -i] origin file");
+	System.exit(1);
+}
+
+public static void
+main(String [] args) throws Exception {
+	boolean time = false;
+	boolean axfr = false;
+	boolean iterator = false;
+	int arg = 0;
+
+	if (args.length < 2)
+		usage();
+
+	while (args.length - arg > 2) {
+		if (args[0].equals("-t"))
+			time = true;
+		else if (args[0].equals("-a"))
+			axfr = true;
+		else if (args[0].equals("-i"))
+			iterator = true;
+		arg++;
+	}
+
+	Name origin = Name.fromString(args[arg++], Name.root);
+	String file = args[arg++];
+
+	long start = System.currentTimeMillis();
+	Zone zone = new Zone(origin, file);
+	long end = System.currentTimeMillis();
+	if (axfr) {
+		Iterator it = zone.AXFR();
+		while (it.hasNext()) {
+			System.out.println(it.next());
+		}
+	} else if (iterator) {
+		Iterator it = zone.iterator();
+		while (it.hasNext()) {
+			System.out.println(it.next());
+		}
+	} else {
+		System.out.println(zone);
+	}
+	if (time)
+		System.out.println("; Load time: " + (end - start) + " ms");
+}
+
+}
diff --git a/src/org/xbill/DNS/tests/xfrin.java b/src/org/xbill/DNS/tests/xfrin.java
new file mode 100644
index 0000000..066c70e
--- /dev/null
+++ b/src/org/xbill/DNS/tests/xfrin.java
@@ -0,0 +1,109 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.tests;
+
+import java.util.*;
+import org.xbill.DNS.*;
+
+public class xfrin {
+
+private static void
+usage(String s) {
+	System.out.println("Error: " + s);
+	System.out.println("usage: xfrin [-i serial] [-k keyname/secret] " +
+			   "[-s server] [-p port] [-f] zone");
+	System.exit(1);
+}
+
+public static void
+main(String [] args) throws Exception {
+	ZoneTransferIn xfrin;
+	TSIG key = null;
+	int ixfr_serial = -1;
+	String server = null;
+	int port = SimpleResolver.DEFAULT_PORT;
+	boolean fallback = false;
+	Name zname;
+
+	int arg = 0;
+	while (arg < args.length) {
+		if (args[arg].equals("-i")) {
+			ixfr_serial = Integer.parseInt(args[++arg]);
+			if (ixfr_serial < 0)
+				usage("invalid serial number");
+		} else if (args[arg].equals("-k")) {
+			String s = args[++arg];
+			int index = s.indexOf('/');
+			if (index < 0)
+				usage("invalid key");
+			key = new TSIG(s.substring(0, index),
+				       s.substring(index+1));
+		} else if (args[arg].equals("-s")) {
+			server = args[++arg];
+		} else if (args[arg].equals("-p")) {
+			port = Integer.parseInt(args[++arg]);
+			if (port < 0 || port > 0xFFFF)
+				usage("invalid port");
+		} else if (args[arg].equals("-f")) {
+			fallback = true;
+		} else if (args[arg].startsWith("-")) {
+			usage("invalid option");
+		} else {
+			break;
+		}
+		arg++;
+	}
+	if (arg >= args.length)
+		usage("no zone name specified");
+	zname = Name.fromString(args[arg]);
+
+	if (server == null) {
+		Lookup l = new Lookup(zname, Type.NS);
+		Record [] ns = l.run();
+		if (ns == null) {
+			System.out.println("failed to look up NS record: " +
+					   l.getErrorString());
+			System.exit(1);
+		}
+		server = ns[0].rdataToString();
+		System.out.println("sending to server '" + server + "'");
+	}
+
+	if (ixfr_serial >= 0)
+		xfrin = ZoneTransferIn.newIXFR(zname, ixfr_serial, fallback,
+					       server, port, key);
+	else
+		xfrin = ZoneTransferIn.newAXFR(zname, server, port, key);
+
+	List response = xfrin.run();
+	if (xfrin.isAXFR()) {
+		if (ixfr_serial >= 0)
+			System.out.println("AXFR-like IXFR response");
+		else
+			System.out.println("AXFR response");
+		Iterator it = response.iterator();
+		while (it.hasNext())
+			System.out.println(it.next());
+	} else if (xfrin.isIXFR()) {
+		System.out.println("IXFR response");
+		Iterator it = response.iterator();
+		while (it.hasNext()) {
+			ZoneTransferIn.Delta delta;
+			delta = (ZoneTransferIn.Delta) it.next();
+			System.out.println("delta from " + delta.start +
+					   " to " + delta.end);
+			System.out.println("deletes");
+			Iterator it2 = delta.deletes.iterator();
+			while (it2.hasNext())
+				System.out.println(it2.next());
+			System.out.println("adds");
+			it2 = delta.adds.iterator();
+			while (it2.hasNext())
+				System.out.println(it2.next());
+		}
+	} else if (xfrin.isCurrent()) {
+		System.out.println("up to date");
+	}
+}
+
+}
diff --git a/src/org/xbill/DNS/utils/HMAC.java b/src/org/xbill/DNS/utils/HMAC.java
new file mode 100644
index 0000000..5eb5afd
--- /dev/null
+++ b/src/org/xbill/DNS/utils/HMAC.java
@@ -0,0 +1,182 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.utils;
+
+import java.util.Arrays;
+import java.security.*;
+
+/**
+ * An implementation of the HMAC message authentication code.
+ *
+ * @author Brian Wellington
+ */
+
+public class HMAC {
+
+private MessageDigest digest;
+private int blockLength;
+
+private byte [] ipad, opad;
+
+private static final byte IPAD = 0x36;
+private static final byte OPAD = 0x5c;
+
+private void
+init(byte [] key) {
+	int i;
+
+	if (key.length > blockLength) {
+		key = digest.digest(key);
+		digest.reset();
+	}
+	ipad = new byte[blockLength];
+	opad = new byte[blockLength];
+	for (i = 0; i < key.length; i++) {
+		ipad[i] = (byte) (key[i] ^ IPAD);
+		opad[i] = (byte) (key[i] ^ OPAD);
+	}
+	for (; i < blockLength; i++) {
+		ipad[i] = IPAD;
+		opad[i] = OPAD;
+	}
+	digest.update(ipad);
+}
+
+/**
+ * Creates a new HMAC instance
+ * @param digest The message digest object.
+ * @param blockLength The block length of the message digest.
+ * @param key The secret key
+ */
+public
+HMAC(MessageDigest digest, int blockLength, byte [] key) {
+	digest.reset();
+	this.digest = digest;
+  	this.blockLength = blockLength;
+	init(key);
+}
+
+/**
+ * Creates a new HMAC instance
+ * @param digestName The name of the message digest function.
+ * @param blockLength The block length of the message digest.
+ * @param key The secret key.
+ */
+public
+HMAC(String digestName, int blockLength, byte [] key) {
+	try {
+		digest = MessageDigest.getInstance(digestName);
+	} catch (NoSuchAlgorithmException e) {
+		throw new IllegalArgumentException("unknown digest algorithm "
+						   + digestName);
+	}
+	this.blockLength = blockLength;
+	init(key);
+}
+
+/**
+ * Creates a new HMAC instance
+ * @param digest The message digest object.
+ * @param key The secret key
+ * @deprecated won't work with digests using a padding length other than 64;
+ *             use {@code HMAC(MessageDigest digest, int blockLength,
+ *             byte [] key)} instead.
+ * @see        HMAC#HMAC(MessageDigest digest, int blockLength, byte [] key)
+ */
+public
+HMAC(MessageDigest digest, byte [] key) {
+	this(digest, 64, key);
+}
+
+/**
+ * Creates a new HMAC instance
+ * @param digestName The name of the message digest function.
+ * @param key The secret key.
+ * @deprecated won't work with digests using a padding length other than 64;
+ *             use {@code HMAC(String digestName, int blockLength, byte [] key)}
+ *             instead
+ * @see        HMAC#HMAC(String digestName, int blockLength, byte [] key)
+ */
+public
+HMAC(String digestName, byte [] key) {
+	this(digestName, 64, key);
+}
+
+/**
+ * Adds data to the current hash
+ * @param b The data
+ * @param offset The index at which to start adding to the hash
+ * @param length The number of bytes to hash
+ */
+public void
+update(byte [] b, int offset, int length) {
+	digest.update(b, offset, length);
+}
+
+/**
+ * Adds data to the current hash
+ * @param b The data
+ */
+public void
+update(byte [] b) {
+	digest.update(b);
+}
+
+/**
+ * Signs the data (computes the secure hash)
+ * @return An array with the signature
+ */
+public byte []
+sign() {
+	byte [] output = digest.digest();
+	digest.reset();
+	digest.update(opad);
+	return digest.digest(output);
+}
+
+/**
+ * Verifies the data (computes the secure hash and compares it to the input)
+ * @param signature The signature to compare against
+ * @return true if the signature matches, false otherwise
+ */
+public boolean
+verify(byte [] signature) {
+	return verify(signature, false);
+}
+
+/**
+ * Verifies the data (computes the secure hash and compares it to the input)
+ * @param signature The signature to compare against
+ * @param truncation_ok If true, the signature may be truncated; only the
+ * number of bytes in the provided signature are compared.
+ * @return true if the signature matches, false otherwise
+ */
+public boolean
+verify(byte [] signature, boolean truncation_ok) {
+	byte [] expected = sign();
+	if (truncation_ok && signature.length < expected.length) {
+		byte [] truncated = new byte[signature.length];
+		System.arraycopy(expected, 0, truncated, 0, truncated.length);
+		expected = truncated;
+	}
+	return Arrays.equals(signature, expected);
+}
+
+/**
+ * Resets the HMAC object for further use
+ */
+public void
+clear() {
+	digest.reset();
+	digest.update(ipad);
+}
+
+/**
+ * Returns the length of the digest.
+ */
+public int
+digestLength() {
+	return digest.getDigestLength();
+}
+
+}
diff --git a/src/org/xbill/DNS/utils/base16.java b/src/org/xbill/DNS/utils/base16.java
new file mode 100644
index 0000000..58024e6
--- /dev/null
+++ b/src/org/xbill/DNS/utils/base16.java
@@ -0,0 +1,73 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.utils;
+
+import java.io.*;
+
+/**
+ * Routines for converting between Strings of hex-encoded data and arrays of
+ * binary data.  This is not actually used by DNS.
+ *
+ * @author Brian Wellington
+ */
+
+public class base16 {
+
+private static final String Base16 = "0123456789ABCDEF";
+
+private
+base16() {}
+
+/**
+ * Convert binary data to a hex-encoded String
+ * @param b An array containing binary data
+ * @return A String containing the encoded data
+ */
+public static String
+toString(byte [] b) {
+	ByteArrayOutputStream os = new ByteArrayOutputStream();
+
+	for (int i = 0; i < b.length; i++) {
+		short value = (short) (b[i] & 0xFF);
+		byte high = (byte) (value >> 4);
+		byte low = (byte) (value & 0xF);
+		os.write(Base16.charAt(high));
+		os.write(Base16.charAt(low));
+	}
+	return new String(os.toByteArray());
+}
+
+/**
+ * Convert a hex-encoded String to binary data
+ * @param str A String containing the encoded data
+ * @return An array containing the binary data, or null if the string is invalid
+ */
+public static byte []
+fromString(String str) {
+	ByteArrayOutputStream bs = new ByteArrayOutputStream();
+	byte [] raw = str.getBytes();
+	for (int i = 0; i < raw.length; i++) {
+		if (!Character.isWhitespace((char)raw[i]))
+			bs.write(raw[i]);
+	}
+	byte [] in = bs.toByteArray();
+	if (in.length % 2 != 0) {
+		return null;
+	}
+
+	bs.reset();
+	DataOutputStream ds = new DataOutputStream(bs);
+
+	for (int i = 0; i < in.length; i += 2) {
+		byte high = (byte) Base16.indexOf(Character.toUpperCase((char)in[i]));
+		byte low = (byte) Base16.indexOf(Character.toUpperCase((char)in[i+1]));
+		try {
+			ds.writeByte((high << 4) + low);
+		}
+		catch (IOException e) {
+		}
+	}
+	return bs.toByteArray();
+}
+
+}
diff --git a/src/org/xbill/DNS/utils/base32.java b/src/org/xbill/DNS/utils/base32.java
new file mode 100644
index 0000000..a2f26ea
--- /dev/null
+++ b/src/org/xbill/DNS/utils/base32.java
@@ -0,0 +1,213 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.utils;
+
+import java.io.*;
+
+/**
+ * Routines for converting between Strings of base32-encoded data and arrays
+ * of binary data.  This currently supports the base32 and base32hex alphabets
+ * specified in RFC 4648, sections 6 and 7.
+ * 
+ * @author Brian Wellington
+ */
+
+public class base32 {
+
+public static class Alphabet {
+	private Alphabet() {}
+
+	public static final String BASE32 =
+		"ABCDEFGHIJKLMNOPQRSTUVWXYZ234567=";
+	public static final String BASE32HEX =
+		"0123456789ABCDEFGHIJKLMNOPQRSTUV=";
+};
+
+private String alphabet;
+private boolean padding, lowercase;
+
+/**
+ * Creates an object that can be used to do base32 conversions.
+ * @param alphabet Which alphabet should be used
+ * @param padding Whether padding should be used
+ * @param lowercase Whether lowercase characters should be used.
+ * default parameters (The standard base32 alphabet, no padding, uppercase)
+ */
+public
+base32(String alphabet, boolean padding, boolean lowercase) {
+	this.alphabet = alphabet;
+	this.padding = padding;
+	this.lowercase = lowercase;
+}
+
+static private int
+blockLenToPadding(int blocklen) {
+	switch (blocklen) {
+	case 1:
+		return 6;
+	case 2:
+		return 4;
+	case 3:
+		return 3;
+	case 4:
+		return 1;
+	case 5:
+		return 0;
+	default:
+		return -1;
+	}
+}
+
+static private int
+paddingToBlockLen(int padlen) {
+	switch (padlen) {
+	case 6:
+		return 1;
+	case 4:
+		return 2;
+	case 3:
+		return 3;
+	case 1:
+		return 4;
+	case 0:
+		return 5;
+	default :
+		return -1;
+	}
+}
+
+/**
+ * Convert binary data to a base32-encoded String
+ * 
+ * @param b An array containing binary data
+ * @return A String containing the encoded data
+ */
+public String
+toString(byte [] b) {
+	ByteArrayOutputStream os = new ByteArrayOutputStream();
+
+	for (int i = 0; i < (b.length + 4) / 5; i++) {
+		short s[] = new short[5];
+		int t[] = new int[8];
+
+		int blocklen = 5;
+		for (int j = 0; j < 5; j++) {
+			if ((i * 5 + j) < b.length)
+				s[j] = (short) (b[i * 5 + j] & 0xFF);
+			else {
+				s[j] = 0;
+				blocklen--;
+			}
+		}
+		int padlen = blockLenToPadding(blocklen);
+
+		// convert the 5 byte block into 8 characters (values 0-31).
+
+		// upper 5 bits from first byte
+		t[0] = (byte) ((s[0] >> 3) & 0x1F);
+		// lower 3 bits from 1st byte, upper 2 bits from 2nd.
+		t[1] = (byte) (((s[0] & 0x07) << 2) | ((s[1] >> 6) & 0x03));
+		// bits 5-1 from 2nd.
+		t[2] = (byte) ((s[1] >> 1) & 0x1F);
+		// lower 1 bit from 2nd, upper 4 from 3rd
+		t[3] = (byte) (((s[1] & 0x01) << 4) | ((s[2] >> 4) & 0x0F));
+		// lower 4 from 3rd, upper 1 from 4th.
+		t[4] = (byte) (((s[2] & 0x0F) << 1) | ((s[3] >> 7) & 0x01));
+		// bits 6-2 from 4th
+		t[5] = (byte) ((s[3] >> 2) & 0x1F);
+		// lower 2 from 4th, upper 3 from 5th;
+		t[6] = (byte) (((s[3] & 0x03) << 3) | ((s[4] >> 5) & 0x07));
+		// lower 5 from 5th;
+		t[7] = (byte) (s[4] & 0x1F);
+
+		// write out the actual characters.
+		for (int j = 0; j < t.length - padlen; j++) {
+			char c = alphabet.charAt(t[j]);
+			if (lowercase)
+				c = Character.toLowerCase(c);
+			os.write(c);
+		}
+
+		// write out the padding (if any)
+		if (padding) {
+			for (int j = t.length - padlen; j < t.length; j++)
+				os.write('=');
+		}
+	}
+
+    return new String(os.toByteArray());
+}
+
+/**
+ * Convert a base32-encoded String to binary data
+ * 
+ * @param str A String containing the encoded data
+ * @return An array containing the binary data, or null if the string is invalid
+ */
+public byte[]
+fromString(String str) {
+	ByteArrayOutputStream bs = new ByteArrayOutputStream();
+	byte [] raw = str.getBytes();
+	for (int i = 0; i < raw.length; i++)
+	{
+		char c = (char) raw[i];
+		if (!Character.isWhitespace(c)) {
+			c = Character.toUpperCase(c);
+			bs.write((byte) c);
+		}
+	}
+
+	if (padding) {
+		if (bs.size() % 8 != 0)
+			return null;
+	} else {
+		while (bs.size() % 8 != 0)
+			bs.write('=');
+	}
+
+	byte [] in = bs.toByteArray();
+
+	bs.reset();
+	DataOutputStream ds = new DataOutputStream(bs);
+
+	for (int i = 0; i < in.length / 8; i++) {
+		short[] s = new short[8];
+		int[] t = new int[5];
+
+		int padlen = 8;
+		for (int j = 0; j < 8; j++) {
+			char c = (char) in[i * 8 + j];
+			if (c == '=')
+				break;
+			s[j] = (short) alphabet.indexOf(in[i * 8 + j]);
+			if (s[j] < 0)
+				return null;
+			padlen--;
+		}
+		int blocklen = paddingToBlockLen(padlen);
+		if (blocklen < 0)
+			return null;
+
+		// all 5 bits of 1st, high 3 (of 5) of 2nd
+		t[0] = (s[0] << 3) | s[1] >> 2;
+		// lower 2 of 2nd, all 5 of 3rd, high 1 of 4th
+		t[1] = ((s[1] & 0x03) << 6) | (s[2] << 1) | (s[3] >> 4);
+		// lower 4 of 4th, high 4 of 5th
+		t[2] = ((s[3] & 0x0F) << 4) | ((s[4] >> 1) & 0x0F);
+		// lower 1 of 5th, all 5 of 6th, high 2 of 7th
+		t[3] = (s[4] << 7) | (s[5] << 2) | (s[6] >> 3);
+		// lower 3 of 7th, all of 8th
+		t[4] = ((s[6] & 0x07) << 5) | s[7];
+
+		try {
+			for (int j = 0; j < blocklen; j++)
+				ds.writeByte((byte) (t[j] & 0xFF));
+		}
+		catch (IOException e) {
+		}
+	}
+
+    return bs.toByteArray();
+}
+
+}
diff --git a/src/org/xbill/DNS/utils/base64.java b/src/org/xbill/DNS/utils/base64.java
new file mode 100644
index 0000000..54567cf
--- /dev/null
+++ b/src/org/xbill/DNS/utils/base64.java
@@ -0,0 +1,145 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.utils;
+
+import java.io.*;
+
+/**
+ * Routines for converting between Strings of base64-encoded data and arrays of
+ * binary data.
+ *
+ * @author Brian Wellington
+ */
+
+public class base64 {
+
+private static final String Base64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
+
+private
+base64() {}
+
+/**
+ * Convert binary data to a base64-encoded String
+ * @param b An array containing binary data
+ * @return A String containing the encoded data
+ */
+public static String
+toString(byte [] b) {
+	ByteArrayOutputStream os = new ByteArrayOutputStream();
+
+	for (int i = 0; i < (b.length + 2) / 3; i++) {
+		short [] s = new short[3];
+		short [] t = new short[4];
+		for (int j = 0; j < 3; j++) {
+			if ((i * 3 + j) < b.length)
+				s[j] = (short) (b[i*3+j] & 0xFF);
+			else
+				s[j] = -1;
+		}
+		
+		t[0] = (short) (s[0] >> 2);
+		if (s[1] == -1)
+			t[1] = (short) (((s[0] & 0x3) << 4));
+		else
+			t[1] = (short) (((s[0] & 0x3) << 4) + (s[1] >> 4));
+		if (s[1] == -1)
+			t[2] = t[3] = 64;
+		else if (s[2] == -1) {
+			t[2] = (short) (((s[1] & 0xF) << 2));
+			t[3] = 64;
+		}
+		else {
+			t[2] = (short) (((s[1] & 0xF) << 2) + (s[2] >> 6));
+			t[3] = (short) (s[2] & 0x3F);
+		}
+		for (int j = 0; j < 4; j++)
+			os.write(Base64.charAt(t[j]));
+	}
+	return new String(os.toByteArray());
+}
+
+/**
+ * Formats data into a nicely formatted base64 encoded String
+ * @param b An array containing binary data
+ * @param lineLength The number of characters per line
+ * @param prefix A string prefixing the characters on each line
+ * @param addClose Whether to add a close parenthesis or not
+ * @return A String representing the formatted output
+ */
+public static String
+formatString(byte [] b, int lineLength, String prefix, boolean addClose) {
+	String s = toString(b);
+	StringBuffer sb = new StringBuffer();
+	for (int i = 0; i < s.length(); i += lineLength) {
+		sb.append (prefix);
+		if (i + lineLength >= s.length()) {
+			sb.append(s.substring(i));
+			if (addClose)
+				sb.append(" )");
+		}
+		else {
+			sb.append(s.substring(i, i + lineLength));
+			sb.append("\n");
+		}
+	}
+	return sb.toString();
+}
+
+
+/**
+ * Convert a base64-encoded String to binary data
+ * @param str A String containing the encoded data
+ * @return An array containing the binary data, or null if the string is invalid
+ */
+public static byte []
+fromString(String str) {
+	ByteArrayOutputStream bs = new ByteArrayOutputStream();
+	byte [] raw = str.getBytes();
+	for (int i = 0; i < raw.length; i++) {
+		if (!Character.isWhitespace((char)raw[i]))
+			bs.write(raw[i]);
+	}
+	byte [] in = bs.toByteArray();
+	if (in.length % 4 != 0) {
+		return null;
+	}
+
+	bs.reset();
+	DataOutputStream ds = new DataOutputStream(bs);
+
+	for (int i = 0; i < (in.length + 3) / 4; i++) {
+		short [] s = new short[4];
+		short [] t = new short[3];
+
+		for (int j = 0; j < 4; j++)
+			s[j] = (short) Base64.indexOf(in[i*4+j]);
+
+		t[0] = (short) ((s[0] << 2) + (s[1] >> 4));
+		if (s[2] == 64) {
+			t[1] = t[2] = (short) (-1);
+			if ((s[1] & 0xF) != 0)
+				return null;
+		}
+		else if (s[3] == 64) {
+			t[1] = (short) (((s[1] << 4) + (s[2] >> 2)) & 0xFF);
+			t[2] = (short) (-1);
+			if ((s[2] & 0x3) != 0)
+				return null;
+		}
+		else {
+			t[1] = (short) (((s[1] << 4) + (s[2] >> 2)) & 0xFF);
+			t[2] = (short) (((s[2] << 6) + s[3]) & 0xFF);
+		}
+
+		try {
+			for (int j = 0; j < 3; j++)
+				if (t[j] >= 0)
+					ds.writeByte(t[j]);
+		}
+		catch (IOException e) {
+		}
+	}
+	return bs.toByteArray();
+}
+
+}
diff --git a/src/org/xbill/DNS/utils/hexdump.java b/src/org/xbill/DNS/utils/hexdump.java
new file mode 100644
index 0000000..1a79a40
--- /dev/null
+++ b/src/org/xbill/DNS/utils/hexdump.java
@@ -0,0 +1,56 @@
+// Copyright (c) 1999-2004 Brian Wellington (bwelling@xbill.org)
+
+package org.xbill.DNS.utils;
+
+/**
+ * A routine to produce a nice looking hex dump
+ *
+ * @author Brian Wellington
+ */
+
+public class hexdump {
+
+private static final char [] hex = "0123456789ABCDEF".toCharArray();
+
+/**
+ * Dumps a byte array into hex format.
+ * @param description If not null, a description of the data.
+ * @param b The data to be printed.
+ * @param offset The start of the data in the array.
+ * @param length The length of the data in the array.
+ */
+public static String
+dump(String description, byte [] b, int offset, int length) {
+	StringBuffer sb = new StringBuffer();
+
+	sb.append(length + "b");
+	if (description != null)
+		sb.append(" (" + description + ")");
+	sb.append(':');
+
+	int prefixlen = sb.toString().length();
+	prefixlen = (prefixlen + 8) & ~ 7;
+	sb.append('\t');
+
+	int perline = (80 - prefixlen) / 3;
+	for (int i = 0; i < length; i++) {
+		if (i != 0 && i % perline == 0) {
+			sb.append('\n');
+			for (int j = 0; j < prefixlen / 8 ; j++)
+				sb.append('\t');
+		}
+		int value = (int)(b[i + offset]) & 0xFF;
+		sb.append(hex[(value >> 4)]);
+		sb.append(hex[(value & 0xF)]);
+		sb.append(' ');
+	}
+	sb.append('\n');
+	return sb.toString();
+}
+
+public static String
+dump(String s, byte [] b) {
+	return dump(s, b, 0, b.length);
+}
+
+}
diff --git a/src/org/xbill/DNS/windows/DNSServer.properties b/src/org/xbill/DNS/windows/DNSServer.properties
new file mode 100644
index 0000000..25342f9
--- /dev/null
+++ b/src/org/xbill/DNS/windows/DNSServer.properties
@@ -0,0 +1,4 @@
+host_name=Host Name
+primary_dns_suffix=Primary Dns Suffix
+dns_suffix=DNS Suffix
+dns_servers=DNS Servers
diff --git a/src/org/xbill/DNS/windows/DNSServer_de.properties b/src/org/xbill/DNS/windows/DNSServer_de.properties
new file mode 100644
index 0000000..aa3f4a6
--- /dev/null
+++ b/src/org/xbill/DNS/windows/DNSServer_de.properties
@@ -0,0 +1,4 @@
+host_name=Hostname
+primary_dns_suffix=Prim\u00E4res DNS-Suffix
+dns_suffix=DNS-Suffixsuchliste
+dns_servers=DNS-Server
diff --git a/src/org/xbill/DNS/windows/DNSServer_fr.properties b/src/org/xbill/DNS/windows/DNSServer_fr.properties
new file mode 100644
index 0000000..7c87a25
--- /dev/null
+++ b/src/org/xbill/DNS/windows/DNSServer_fr.properties
@@ -0,0 +1,4 @@
+host_name=Nom de l'h\u00F4te
+primary_dns_suffix=Suffixe DNS principal
+dns_suffix=Suffixe DNS propre \u00E0 la connexion
+dns_servers=Serveurs DNS
diff --git a/src/org/xbill/DNS/windows/DNSServer_ja.properties b/src/org/xbill/DNS/windows/DNSServer_ja.properties
new file mode 100644
index 0000000..f873164
--- /dev/null
+++ b/src/org/xbill/DNS/windows/DNSServer_ja.properties
@@ -0,0 +1,4 @@
+host_name=\u30db\u30b9\u30c8\u540d
+primary_dns_suffix=\u30d7\u30e9\u30a4\u30de\u30ea DNS \u30b5\u30d5\u30a3\u30c3\u30af\u30b9
+dns_suffix=DNS \u30b5\u30d5\u30a3\u30c3\u30af\u30b9
+dns_servers=DNS \u30b5\u30fc\u30d0\u30fc
diff --git a/src/org/xbill/DNS/windows/DNSServer_pl.properties b/src/org/xbill/DNS/windows/DNSServer_pl.properties
new file mode 100644
index 0000000..eab5774
--- /dev/null
+++ b/src/org/xbill/DNS/windows/DNSServer_pl.properties
@@ -0,0 +1,4 @@
+host_name=Nazwa hosta
+primary_dns_suffix=Sufiks podstawowej domeny DNS
+dns_suffix=Sufiks DNS konkretnego po\u0142\u0105czenia
+dns_servers=Serwery DNS
diff --git a/src/overview.html b/src/overview.html
new file mode 100644
index 0000000..a2449b1
--- /dev/null
+++ b/src/overview.html
@@ -0,0 +1,4 @@
+<body>API specification for <a href="http://www.jivesoftware.org/smack">Smack</a>, an Open Source XMPP client library.
+<p>
+The {@link org.jivesoftware.smack.Connection} class is the main entry point for the API.
+</body>
diff --git a/update.sh b/update.sh
new file mode 100755
index 0000000..9826c7b
--- /dev/null
+++ b/update.sh
@@ -0,0 +1,8 @@
+#!/bin/bash
+
+rm -rf src
+cd asmack-master
+rm -rf src build
+./build.bash
+mv build/src/trunk ../src
+rm -rf src build
