private synchronized void connectIfNecessary() {
    if (server == null || delegate.isConnected()) {
      return;
    }

    try {
      delegate.connect(server, connectionTimeout);
    } catch (IOException e) {
      LOGGER.warn("Auto-reconnect failed", e);
    }
  }
  @Override
  public synchronized void connect(InetSocketAddress addr, long timeout) throws IOException {
    this.server = addr;
    this.connectionTimeout = timeout;

    delegate.connect(addr, timeout);
  }
  @Override
  public Long send(SocketManager socketManager) throws IOException {
    String response = socketManager.sendAndWait(getMessage());

    try {
      return Long.parseLong(response);
    } catch (NumberFormatException e) {
      /*
       * If unable to determine uptime, the string "Could not determine uptime." is
       * returned.
       */
      return -1l;
    }
  }
 @Override
 public String sendAndWait(String message) throws IOException {
   connectIfNecessary();
   return delegate.sendAndWait(message);
 }
 @Override
 public void send(String message) throws IOException {
   connectIfNecessary();
   delegate.send(message);
 }
 @Override
 public synchronized void disconnect() {
   this.server = null;
   delegate.disconnect();
 }
 @Override
 public SocketManager newConnection() throws IOException {
   connectIfNecessary();
   return delegate.newConnection();
 }
 @Override
 public InetSocketAddress getConnectedAddress() {
   connectIfNecessary();
   return delegate.getConnectedAddress();
 }
 @Override
 public boolean isConnected() {
   connectIfNecessary();
   return delegate.isConnected();
 }
 @Override
 public long getDefaultMessageTimeout(TimeUnit unit) {
   return delegate.getDefaultMessageTimeout(unit);
 }
 @Override
 public void setDefaultMessageTimeout(long time, TimeUnit unit) {
   delegate.setDefaultMessageTimeout(time, unit);
 }
 @Override
 public void setInterceptor(Interceptor interceptor) {
   delegate.setInterceptor(interceptor);
 }
 @Override
 public ByteChannel redirectChannel() {
   connectIfNecessary();
   return delegate.redirectChannel();
 }
 @Override
 public String sendAndWait(String message, long timeout, TimeUnit unit) throws IOException {
   connectIfNecessary();
   return delegate.sendAndWait(message, timeout, unit);
 }
 @Override
 public List<Channel> send(SocketManager socketManager) throws IOException {
   String response = socketManager.sendAndWait(getMessage());
   return Control0_24Utils.parseChannels(response);
 }