@Override
        public void run() {
                DisconnectCause disconnectCause = DisconnectCause.OTHER;
                try {
                        while (true) {
                                Object msg = null;
                                try {
                                        msg = queue.take();
                                } catch (InterruptedException ie) {
                                        continue;
                                }
                                if (msg instanceof SendPacketMessage) {
                                        writer.sendMessage(msg);
                                } else if (msg instanceof PacketReceivedMessage) {
                                        output.sendMessage(msg);
                                } else if (msg instanceof ShutdownMessage) {
                                        break;
                                } else if (msg instanceof SocketDisconnectedMessage) {
                                        disconnectCause = ((SocketDisconnectedMessage)msg).cause;
                                        break;
                                } else {
                                        WinLinkPlugin.getInstance().getLogger().warning(getClass().getSimpleName() + " bad message type: " + msg.getClass().getName());
                                }
                        }
                        writer.shutdown();
                        reader.shutdown();
                        try { socket.close(); } catch (IOException ioe) {}
                        output.sendMessage(new SocketDisconnectedMessage(this, disconnectCause));
                } catch (Exception e) {
                        e.printStackTrace();
                }
        }