/** * 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. PacketWriter packetWriter = this.packetWriter; if (packetWriter != null) { packetWriter.sendPacket(unavailablePresence); } this.setWasAuthenticated(authenticated); authenticated = false; connected = false; PacketReader packetReader = this.packetReader; if (packetReader != null) { packetReader.shutdown(); } packetWriter = this.packetWriter; if (packetWriter != null) { packetWriter.shutdown(); } // Wait 150 ms for processes to clean-up, then shutdown. try { Thread.sleep(150); } catch (Exception e) { // Ignore. } // Close down the readers and writers. Reader reader = this.reader; if (reader != null) { try { reader.close(); } catch (Throwable ignore) { /* ignore */ } this.reader = null; } Writer writer = this.writer; if (writer != null) { try { writer.close(); } catch (Throwable ignore) { /* ignore */ } this.writer = null; } try { socket.close(); } catch (Exception e) { // Ignore. } saslAuthentication.init(); }
/** * 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 { PacketReader packetReader = this.packetReader; PacketWriter packetWriter = this.packetWriter; boolean isFirstInitialization = packetReader == null || packetWriter == null; usingCompression = false; // Set the reader and writer instance variables initReaderAndWriter(); try { if (isFirstInitialization) { this.packetWriter = packetWriter = new PacketWriter(this); this.packetReader = 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; // Start keep alive process (after TLS was negotiated - if available) packetWriter.startKeepAliveProcess(); if (isFirstInitialization) { // Notify listeners that a new connection has been established for (ConnectionCreationListener listener : getConnectionCreationListeners()) { listener.connectionCreated(this); } } else if (!wasAuthenticated) { packetReader.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 */ } this.packetWriter = null; } if (packetReader != null) { try { packetReader.shutdown(); } catch (Throwable ignore) { /* ignore */ } this.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. } }