public void stop() {
    log.info("Shutting down proxy");
    if (stopped.get()) {
      log.info("Already stopped");
      return;
    }
    stopped.set(true);

    log.info("Closing all channels...");

    // See http://static.netty.io/3.5/guide/#start.12

    final ChannelGroupFuture future = allChannels.close();
    future.awaitUninterruptibly(10 * 1000);

    if (!future.isCompleteSuccess()) {
      final Iterator<ChannelFuture> iter = future.iterator();
      while (iter.hasNext()) {
        final ChannelFuture cf = iter.next();
        if (!cf.isSuccess()) {
          log.warn("Cause of failure for {} is {}", cf.getChannel(), cf.getCause());
        }
      }
    }
    log.info("Stopping timer");
    timer.stop();
    serverChannelFactory.releaseExternalResources();
    clientChannelFactory.releaseExternalResources();

    log.info("Done shutting down proxy");
  }
 @Override
 public boolean isSuccessful() {
   if (groupFuture != null) {
     return groupFuture.isCompleteSuccess();
   } else {
     return false;
   }
 }
 @Override
 public final boolean isCompleteSuccess() {
   ensureConditionSet();
   if (condition) {
     return backedChannelGroupFuture.isCompleteSuccess();
   }
   return false;
 }
 public void close() throws IOException {
   ChannelGroupFuture f = group.close().awaitUninterruptibly();
   if (!f.isCompleteSuccess()) {
     for (ChannelFuture future : f) {
       if (!future.isSuccess()) {
         throw new IOException(future.getCause());
       }
     }
   }
   bootstrap.releaseExternalResources();
 }