title: asyncsocket ipad doesn't connect to server
body: <p>My application times out while trying to connect to host. The timeout time is set to unlimited so I take it that the client is really just unable to connect at all.</p>
  
  <p>I have an iPad app running asyncsockets and I'm trying to get it to connect to a server on my desktop also using asyncsockets. The iPad is specifically iOS 5 and is using GCD asyncsockets.</p>
  
  <p>The server is being invoked through a NSRunLoop. It receives no form of connection from the client (none of breakpoints are caught like they are for telnet connections).</p>
  
  <p>I'm able to telnet into the server from other machines just fine. I'm also able to connect the iPad client to host:google.com on port:80 just fine.</p>
  
  <p>I've tried connecting the iPad to the server on ports 8080, 4500, and 50000 all to no success (they all work for telnet though).</p>
  
  <p>I believe there is something in the server code causing this but I am not sure.</p>
  
  <p>My server code is from a sample found here: <a href="http://mysterycoconut.com/blog/2010/07/tweak-away/" rel="nofollow noreferrer">http://mysterycoconut.com/blog/2010/07/tweak-away/</a></p>
  
  <p>My client code is modified HTTP client code from the sample GCD code supplied by the asyncsockets repository: <a href="https://github.com/robbiehanson/CocoaAsyncSocket/blob/master/Examples/GCD/SimpleHTTPClient/Mobile/SimpleHTTPClient/SimpleHTTPClientAppDelegate.m" rel="nofollow noreferrer">https://github.com/robbiehanson/CocoaAsyncSocket/blob/master/Examples/GCD/SimpleHTTPClient/Mobile/SimpleHTTPClient/SimpleHTTPClientAppDelegate.m</a></p>
  
  <p>Here is my server code:</p>
  
  <pre><code>  - (id) init;
  {
      self = [super init];
      if (self != nil)
      {
          debugServer = [[AsyncSocket alloc] initWithDelegate:self];
          connectedClients = [[NSMutableArray alloc] initWithCapacity:1];
          running = false;
      }
      return self;
  }
  
  - (void) dealloc;
  {
      [self stop];
      [connectedClients release];
      [debugServer release];
      [super dealloc];
  }
  
  - (void) startOnPort
  {
      if (running) return;
  
      if (_port &lt; 0 || _port &gt; 65535)
          _port = 0;
  
      NSError *error = nil;
      if (![debugServer acceptOnPort:_port error:&amp;error])
          return;
  
      NSLog(@"My Awesome Debug Server has started on port %hu", [debugServer localPort]);
  
      running = true;
  }
  
  
  - (void) stop;
  {
      if (!running) return;
  
      [debugServer disconnect];
      for (AsyncSocket* socket in connectedClients)
          [socket disconnect]; 
  
      running = false;
  }
  
  
  - (void) setPort:(int)in_port{
      _port = in_port;
  }
  
  - (void)onSocket:(AsyncSocket *)socket didAcceptNewSocket:(AsyncSocket *)newSocket;
  {
      [connectedClients addObject:newSocket];
  }
  
  
  - (void)onSocketDidDisconnect:(AsyncSocket *)socket;
  {
      [connectedClients removeObject:socket];
  }
  
  - (void)onSocket:(AsyncSocket *)socket didConnectToHost:(NSString *)host port:(UInt16)port;
  {
      NSLog(@"Accepted client %@:%hu", host, port);
  
      NSData *welcomeData = [@"Welcome to my Awesome Debug Server\r\n\r\n" 
                             dataUsingEncoding:NSUTF8StringEncoding];
      [socket writeData:welcomeData withTimeout:-1 tag:WelcomeMsgTag];
  
      [socket readDataWithTimeout:-1 tag:GenericMsgTag];
  }
  
  
  - (void)onSocket:(AsyncSocket *)socket didReadData:(NSData *)data withTag:(long)tag;
  {
      NSString *tmp = [NSString stringWithUTF8String:[data bytes]];
      NSString *input = [tmp stringByTrimmingCharactersInSet:
                         [NSCharacterSet whitespaceAndNewlineCharacterSet]];
  
      NSLog(@"%@",input);
  
      if ([input isEqualToString:@"exit"])
      {
          NSData *byeData = [@"Bye!\r\n" dataUsingEncoding:NSUTF8StringEncoding];
          [socket writeData:byeData withTimeout:-1 tag:GenericMsgTag];
          [socket disconnectAfterWriting];
          return;
      }
  
      [socket readDataWithTimeout:-1 tag:GenericMsgTag];
  }
  
  @end
  </code></pre>
  
  <p>...and here is my client code:</p>
  
  <pre><code>- (id) init
  {
      if (self = [super init]) {
      // AsyncSocket optionally uses the Lumberjack logging framework.
      // 
      // Lumberjack is a professional logging framework. It's extremely fast and flexible.
      // It also uses GCD, making it a great fit for GCDAsyncSocket.
      // 
      // As mentioned earlier, enabling logging in GCDAsyncSocket is entirely optional.
      // Doing so simply helps give you a deeper understanding of the inner workings of the library (if you care).
      // You can do so at the top of GCDAsyncSocket.m,
      // where you can also control things such as the log level,
      // and whether or not logging should be asynchronous (helps to improve speed, and
      // perfect for reducing interference with those pesky timing bugs in your code).
      // 
      // There is a massive amount of documentation on the Lumberjack project page:
      // https://github.com/CocoaLumberjack/CocoaLumberjack
      // 
      // But this one line is all you need to instruct Lumberjack to spit out log statements to the Xcode console.
  
      [DDLog addLogger:[DDTTYLogger sharedInstance]];
  
      // Create our GCDAsyncSocket instance.
      // 
      // Notice that we give it the normal delegate AND a delegate queue.
      // The socket will do all of its operations in a background queue,
      // and you can tell it which thread/queue to invoke your delegate on.
      // In this case, we're just saying invoke us on the main thread.
      // But you can see how trivial it would be to create your own queue,
      // and parallelize your networking processing code by having your
      // delegate methods invoked and run on background queues.
  
      asyncSocket = [[GCDAsyncSocket alloc] initWithDelegate:self delegateQueue:dispatch_get_main_queue()];
  
      // Now we tell the ASYNCHRONOUS socket to connect.
      // 
      // Recall that GCDAsyncSocket is ... asynchronous.
      // This means when you tell the socket to connect, it will do so ... asynchronously.
      // After all, do you want your main thread to block on a slow network connection?
      // 
      // So what's with the BOOL return value, and error pointer?
      // These are for early detection of obvious problems, such as:
      // 
      // - The socket is already connected.
      // - You passed in an invalid parameter.
      // - The socket isn't configured properly.
      // 
      // The error message might be something like "Attempting to connect without a delegate. Set a delegate first."
      // 
      // When the asynchronous sockets connects, it will invoke the socket:didConnectToHost:port: delegate method.
  
      NSError *error = nil;
  
  #if USE_SECURE_CONNECTION
      uint16_t port = 443; // HTTPS
  #else
      uint16_t port = 8080;  // HTTP
  #endif
  
      DDLogVerbose(@"port: %d\t host: %@",port,@"130.85.92.12");
  
      if (![asyncSocket connectToHost:@"130.85.92.12" onPort:port error:&amp;error])
      {
          DDLogError(@"Unable to connect to due to invalid configuration: %@", error);
      }
      else
      {
          DDLogVerbose(@"Connecting...");
      }
  
  #if USE_SECURE_CONNECTION
  
      // The connect method above is asynchronous.
      // At this point, the connection has been initiated, but hasn't completed.
      // When the connection is establish, our socket:didConnectToHost:port: delegate method will be invoked.
      // 
      // Now, for a secure connection we have to connect to the HTTPS server running on port 443.
      // The SSL/TLS protocol runs atop TCP, so after the connection is established we want to start the TLS handshake.
      // 
      // We already know this is what we want to do.
      // Wouldn't it be convenient if we could tell the socket to queue the security upgrade now instead of waiting?
      // Well in fact you can! This is part of the queued architecture of AsyncSocket.
      // 
      // After the connection has been established, AsyncSocket will look in it's queue for the next task.
      // There it will find, dequeue and execute our request to start the TLS security protocol.
      // 
      // The options passed to the startTLS method are fully documented in the GCDAsyncSocket header file.
      // The deusty server only has a development (self-signed) X.509 certificate.
      // So we tell it not to attempt to validate the cert (cause if it did it would fail).
  
      NSDictionary *options = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:NO]
                                                          forKey:(NSString *)kCFStreamSSLValidatesCertificateChain];
  
      [asyncSocket startTLS:options];
  
  #endif
      }
  
      return self;
  }
  
  - (void)socket:(GCDAsyncSocket *)sock didConnectToHost:(NSString *)host port:(UInt16)port
  {
      DDLogVerbose(@"socket:didConnectToHost:%@ port:%hu", host, port);
  
      // HTTP is a really simple protocol.
      // 
      // If you don't already know all about it, this is one of the best resources I know (short and sweet):
      // http://www.jmarshall.com/easy/http/
      // 
      // We're just going to tell the server to send us the metadata (essentially) about a particular resource.
      // The server will send an http response, and then immediately close the connection.
  
      NSString *msg = @"iOS client connected\r\n\r\n";
      NSData *msgdata = [msg dataUsingEncoding:NSUTF8StringEncoding];
  
      [asyncSocket writeData:msgdata withTimeout:-1.0 tag:0];
  
      // Side Note:
      // 
      // The AsyncSocket family supports queued reads and writes.
      // 
      // This means that you don't have to wait for the socket to connect before issuing your read or write commands.
      // If you do so before the socket is connected, it will simply queue the requests,
      // and process them after the socket is connected.
      // Also, you can issue multiple write commands (or read commands) at a time.
      // You don't have to wait for one write operation to complete before sending another write command.
      // 
      // The whole point is to make YOUR code easier to write, easier to read, and easier to maintain.
      // Do networking stuff when it is easiest for you, or when it makes the most sense for you.
      // AsyncSocket adapts to your schedule, not the other way around.
  
  #if READ_HEADER_LINE_BY_LINE
  
      // Now we tell the socket to read the first line of the http response header.
      // As per the http protocol, we know each header line is terminated with a CRLF (carriage return, line feed).
  
      [asyncSocket readDataToData:[GCDAsyncSocket CRLFData] withTimeout:-1.0 tag:0];
  #else
  
      // Now we tell the socket to read the full header for the http response.
      // As per the http protocol, we know the header is terminated with two CRLF's (carriage return, line feed).
  
      [asyncSocket readDataToData:[GCDAsyncSocket CRLFData] withTimeout:-1.0 tag:0];
  
  #endif
  }
  
  - (void)socketDidSecure:(GCDAsyncSocket *)sock
  {
      // This method will be called if USE_SECURE_CONNECTION is set
  
      DDLogVerbose(@"socketDidSecure:");
  }
  
  - (void)socket:(GCDAsyncSocket *)sock didWriteDataWithTag:(long)tag
  {
      DDLogVerbose(@"socket:didWriteDataWithTag:");
  }
  
  - (void)socket:(GCDAsyncSocket *)sock didReadData:(NSData *)data withTag:(long)tag
  {
      DDLogVerbose(@"socket:didReadData:withTag:");
  
      NSString *httpResponse = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
  
      NSLog(@"%@",httpResponse);
  
  #if READ_HEADER_LINE_BY_LINE
  
      DDLogInfo(@"Line httpResponse: %@", httpResponse);
  
      // As per the http protocol, we know the header is terminated with two CRLF's.
      // In other words, an empty line.
  
      if ([data length] == 2) // 2 bytes = CRLF
      {
          DDLogInfo(@"&lt;done&gt;");
      }
      else
      {
          // Read the next line of the header
          [asyncSocket readDataToData:[GCDAsyncSocket CRLFData] withTimeout:-1.0 tag:0];
      }
  
  #else
  
      DDLogInfo(@"Full httpResponse: %@", httpResponse);
  
  #endif
  
      [httpResponse release];
  }
  
  - (void)socketDidDisconnect:(GCDAsyncSocket *)sock withError:(NSError *)err
  {
      // Since we requested HTTP/1.0, we expect the server to close the connection as soon as it has sent the response.
  
      DDLogVerbose(@"socketDidDisconnect:withError: \"%@\"", err);
  }
  </code></pre>
  
  <p>I've looked around for answers but have had no success. I figured the best course of action would be to ask you all rather than wrack my brain trying to solve it myself.</p>