[
  {
    "path": ".clang-format",
    "content": "---\nBasedOnStyle: Google\nStandard: Cpp11\nColumnLimit: 0\nAlignTrailingComments: false\nNamespaceIndentation: All\nDerivePointerAlignment: false\nAlwaysBreakBeforeMultilineStrings: false\nAccessModifierOffset: -2\nObjCSpaceBeforeProtocolList: true\nSortIncludes: false\n---\nLanguage: ObjC\n...\n"
  },
  {
    "path": ".gitignore",
    "content": ".DS_Store\nxcuserdata\nproject.xcworkspace\n"
  },
  {
    "path": "CLT/main.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTelnetServer.h\"\n#import \"NSMutableString+ANSI.h\"\n\nint main(int argc, const char* argv[]) {\n  @autoreleasepool {\n    GCDTCPServer* server = [[GCDTelnetServer alloc] initWithPort:2323\n        startHandler:^NSString*(GCDTelnetConnection* connection) {\n\n          NSMutableString* string = [[NSMutableString alloc] init];\n          if (connection.colorTerminal) {\n            [string appendANSIString:@\"Welcome in color!\" withColor:kANSIColor_Green bold:NO];\n          } else {\n            [string appendString:@\"Welcome!\"];\n          }\n          [string appendFormat:@\"\\nYou are connected using \\\"%@\\\"\\n\", connection.terminalType];\n          return string;\n\n        }\n        lineHandler:^NSString*(GCDTelnetConnection* connection, NSString* line) {\n\n          return [line stringByAppendingString:@\"\\n\"];\n\n        }];\n    if (![server start]) {\n      abort();\n    }\n    NSLog(@\"Telnet server running on %@\", GCDTCPServerGetPrimaryIPAddress(false));\n    CFRunLoopRun();\n  }\n  return 0;\n}\n"
  },
  {
    "path": "Format-Source.sh",
    "content": "#!/bin/sh -ex\n\n# brew install clang-format\n\nCLANG_FORMAT_VERSION=`clang-format -version | awk '{ print $3 }'`\nif [[ \"$CLANG_FORMAT_VERSION\" != \"5.0.0\" ]]; then\n  echo \"Unsupported clang-format version\"\n  exit 1\nfi\n\npushd \"GCDTelnetServer\"\nclang-format -style=file -i *.h *.m\npopd\npushd \"Tests\"\nclang-format -style=file -i *.m\npopd\n\npushd \"CLT\"\nclang-format -style=file -i *.m\npopd\npushd \"iOS\"\nclang-format -style=file -i *.h *.m\npopd\n\necho \"OK\"\n"
  },
  {
    "path": "GCDNetworking/.clang-format",
    "content": "---\nBasedOnStyle: Google\nStandard: Cpp11\nColumnLimit: 0\nAlignTrailingComments: false\nNamespaceIndentation: All\nDerivePointerAlignment: false\nAlwaysBreakBeforeMultilineStrings: false\nAccessModifierOffset: -2\nObjCSpaceBeforeProtocolList: true\nSortIncludes: false\n---\nLanguage: ObjC\n...\n"
  },
  {
    "path": "GCDNetworking/.gitignore",
    "content": ".DS_Store\nxcuserdata\nproject.xcworkspace\n"
  },
  {
    "path": "GCDNetworking/.travis.yml",
    "content": "language: objective-c\nscript: ./Run-Tests.sh\n"
  },
  {
    "path": "GCDNetworking/CLT/main.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDNetworking.h\"\n\n@interface Connection : GCDTCPServerConnection\n@end\n\n@implementation Connection\n\n- (void)didOpen {\n  [super didOpen];\n\n  NSString* welcome = @\"Hello World!\\n\";\n  [self writeDataAsynchronously:[welcome dataUsingEncoding:NSUTF8StringEncoding]\n                     completion:^(BOOL success) {\n                       [self close];\n                     }];\n}\n\n@end\n\nint main(int argc, const char* argv[]) {\n  @autoreleasepool {\n    GCDTCPServer* server = [[GCDTCPServer alloc] initWithConnectionClass:[Connection class] port:2323];\n    if (![server start]) {\n      abort();\n    }\n    NSLog(@\"TCP server running on %@\", GCDTCPServerGetPrimaryIPAddress(false));\n\n    CFRunLoopRun();\n  }\n  return 0;\n}\n"
  },
  {
    "path": "GCDNetworking/Format-Source.sh",
    "content": "#!/bin/sh -ex\n\n# brew install clang-format\n\nCLANG_FORMAT_VERSION=`clang-format -version | awk '{ print $3 }'`\nif [[ \"$CLANG_FORMAT_VERSION\" != \"5.0.0\" ]]; then\n  echo \"Unsupported clang-format version\"\n  exit 1\nfi\n\npushd \"GCDNetworking\"\nclang-format -style=file -i *.h *.m\npopd\npushd \"Tests\"\nclang-format -style=file -i *.m\npopd\n\npushd \"CLT\"\nclang-format -style=file -i *.m\npopd\npushd \"iOS\"\nclang-format -style=file -i *.h *.m\npopd\n\necho \"OK\"\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDNetworking.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTCPConnection.h\"\n#import \"GCDTCPPeer.h\"\n#import \"GCDTCPClient.h\"\n#import \"GCDTCPServer.h\"\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDNetworkingLoggingBridgePrivate.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <Foundation/Foundation.h>\n\n/**\n *  Automatically detect if XLFacility is available.\n */\n\n#if defined(__has_include) && __has_include(\"XLFacilityMacros.h\")\n\n#define __LOGGING_BRIDGE_XLFACILITY__\n\n#import \"XLFacilityMacros.h\"\n\n#define _LOG_DEBUG(...) XLOG_DEBUG(__VA_ARGS__)\n#define _LOG_VERBOSE(...) XLOG_VERBOSE(__VA_ARGS__)\n#define _LOG_INFO(...) XLOG_INFO(__VA_ARGS__)\n#define _LOG_WARNING(...) XLOG_WARNING(__VA_ARGS__)\n#define _LOG_ERROR(...) XLOG_ERROR(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) XLOG_EXCEPTION(__EXCEPTION__)\n\n#define _LOG_DEBUG_CHECK(__CONDITION__) XLOG_DEBUG_CHECK(__CONDITION__)\n#define _LOG_DEBUG_UNREACHABLE() XLOG_DEBUG_UNREACHABLE()\n\n/**\n *  Automatically detect if CocoaLumberJack is available.\n */\n\n#elif defined(__has_include) && __has_include(\"DDLogMacros.h\")\n\n#import \"DDLogMacros.h\"\n\n#define __LOGGING_BRIDGE_COCOALUMBERJACK__\n\n#undef LOG_LEVEL_DEF\n#define LOG_LEVEL_DEF _LoggingMinLevel\nextern int _LoggingMinLevel;\n\n#define _LOG_DEBUG(...) DDLogDebug(__VA_ARGS__)\n#define _LOG_VERBOSE(...) DDLogVerbose(__VA_ARGS__)\n#define _LOG_INFO(...) DDLogInfo(__VA_ARGS__)\n#define _LOG_WARNING(...) DDLogWarn(__VA_ARGS__)\n#define _LOG_ERROR(...) DDLogError(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) DDLogError(@\"%@\", __EXCEPTION__)\n\n/**\n *  Check if a custom logging header should be used instead.\n */\n\n#elif defined(__LOGGING_CUSTOM_HEADER__)\n\n#define __LOGGING_BRIDGE_CUSTOM__\n\n#import __LOGGING_CUSTOM_HEADER__\n\n/**\n *  If all of the above fail, fall back to NSLog().\n */\n\n#else\n\n#define __LOGGING_BRIDGE_BUILTIN__\n\n#if DEBUG\n#define _LOG_DEBUG(...) NSLog(__VA_ARGS__)\n#define _LOG_VERBOSE(...) NSLog(__VA_ARGS__)\n#define _LOG_INFO(...) NSLog(__VA_ARGS__)\n#else\n#define _LOG_DEBUG(...)\n#define _LOG_VERBOSE(...)\n#define _LOG_INFO(...)\n#endif\n#define _LOG_WARNING(...) NSLog(__VA_ARGS__)\n#define _LOG_ERROR(...) NSLog(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) NSLog(@\"%@\", __EXCEPTION__)\n\n#endif\n\n/**\n *  Consistency check macros.\n */\n\n#if !defined(_LOG_CHECK)\n#define _LOG_CHECK(__CONDITION__) \\\n  do {                            \\\n    if (!(__CONDITION__)) {       \\\n      abort();                    \\\n    }                             \\\n  } while (0)\n#endif\n\n#if !defined(_LOG_DEBUG_CHECK)\n#if DEBUG\n#define _LOG_DEBUG_CHECK(__CONDITION__) _LOG_CHECK(__CONDITION__)\n#else\n#define _LOG_DEBUG_CHECK(__CONDITION__)\n#endif\n#endif\n\n#if !defined(_LOG_UNREACHABLE)\n#define _LOG_UNREACHABLE() abort()\n#endif\n\n#if !defined(_LOG_DEBUG_UNREACHABLE)\n#if DEBUG\n#define _LOG_DEBUG_UNREACHABLE() _LOG_UNREACHABLE()\n#else\n#define _LOG_DEBUG_UNREACHABLE()\n#endif\n#endif\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDNetworkingPrivate.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n/**\n *  All GCDNetworking headers.\n */\n\n#import \"GCDNetworking.h\"\n#import \"GCDNetworkingLoggingBridgePrivate.h\"\n\n/**\n *  GCDNetworking internal constants and APIs.\n */\n\n#define GN_QUEUE_LABEL object_getClassName(self)\n\n#define GN_GLOBAL_DISPATCH_QUEUE dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0)\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPClient.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTCPPeer.h\"\n\n@class GCDTCPClient;\n\n/**\n *  The GCDTCPClientConnection is an abstract class to implement connections\n *  for GCDTCPClient: it cannot be used directly.\n */\n@interface GCDTCPClientConnection : GCDTCPPeerConnection\n@end\n\n/**\n *  The GCDTCPClient is a base class that implements a TCP client. It connects\n *  to IPv4 or IPv6 TCP servers and can be configured to reconnect automatically\n *  if the connection is lost.\n *\n *  @warning GCDTCPClient will only ever have a single connection at a time.\n */\n@interface GCDTCPClient : GCDTCPPeer\n\n/**\n *  Returns the host as specified when the client was initialized.\n */\n@property(nonatomic, readonly) NSString* host;\n\n/**\n *  Returns the port as specified when the client was initialized.\n */\n@property(nonatomic, readonly) NSUInteger port;\n\n/**\n *  Sets the connection timeout.\n *\n *  The default value is 10 seconds.\n */\n@property(nonatomic) NSTimeInterval connectionTimeout;\n\n/**\n *  Sets if GCDTCPClient automatically attempts to reconnnect to the server\n *  if the connection is lost.\n *\n *  If enabled, after the connection is lost, GCDTCPClientLogger will attempt\n *  to reconnect after the minimal allowed interval and then multiply this\n *  interval by 2 after each failure to reconnect until the maximal allowed\n *  interval is reached e.g. 10s, 20s, 40s, 80s...\n *\n *  The default value is YES.\n */\n@property(nonatomic) BOOL automaticallyReconnects;\n\n/**\n *  Sets the minimal reconnection interval after the connection was lost.\n *\n *  The default value is 1 second.\n */\n@property(nonatomic) NSTimeInterval minReconnectInterval;\n\n/**\n *  Sets the maximal reconnection interval after the connection was lost.\n *\n *  The default value is 300 seconds.\n */\n@property(nonatomic) NSTimeInterval maxReconnectInterval;\n\n/**\n *  This method is the designated initializer for the class.\n *\n *  Connection class must be [GCDTCPClientConnection class] or a subclass of it.\n */\n- (instancetype)initWithConnectionClass:(Class)connectionClass host:(NSString*)hostname port:(NSUInteger)port;\n\n@end\n\n@interface GCDTCPClient (Extensions)\n\n/**\n *  Convenience method that returns the single connection.\n */\n@property(nonatomic, readonly) GCDTCPClientConnection* connection;\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPClient.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#if !__has_feature(objc_arc)\n#error GCDNetworking requires ARC\n#endif\n\n#import \"GCDNetworkingPrivate.h\"\n\n@implementation GCDTCPClientConnection\n@end\n\n@interface GCDTCPClient () {\n@private\n  NSUInteger _generation;\n  NSTimeInterval _reconnectionDelay;\n}\n@end\n\n@implementation GCDTCPClient\n\n- (id)init {\n  [self doesNotRecognizeSelector:_cmd];\n  return nil;\n}\n\n- (instancetype)initWithConnectionClass:(Class)connectionClass host:(NSString*)hostname port:(NSUInteger)port {\n  _LOG_DEBUG_CHECK([connectionClass isSubclassOfClass:[GCDTCPClientConnection class]]);\n  _LOG_DEBUG_CHECK(hostname);\n  _LOG_DEBUG_CHECK(port > 0);\n  if ((self = [super initWithConnectionClass:connectionClass])) {\n    _host = [hostname copy];\n    _port = port;\n\n    _connectionTimeout = 10.0;\n    _automaticallyReconnects = YES;\n    _minReconnectInterval = 1.0;\n    _maxReconnectInterval = 300.0;\n    _reconnectionDelay = 1.0;\n  }\n  return self;\n}\n\n// Must be called inside lock queue\n- (void)_scheduleReconnection {\n  _LOG_DEBUG(@\"%@ will attempt to reconnect to \\\"%@:%i\\\" in %.0f seconds\", [self class], _host, (int)_port, _reconnectionDelay);\n  dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(_reconnectionDelay * NSEC_PER_SEC)), GN_GLOBAL_DISPATCH_QUEUE, ^{\n    dispatch_sync(self.lockQueue, ^{\n      if (_reconnectionDelay > 0.0) {\n        [self _reconnect];\n      }\n    });\n  });\n  _reconnectionDelay = MIN(2.0 * _reconnectionDelay, _maxReconnectInterval);\n}\n\n- (void)_reconnect {\n  _LOG_DEBUG(@\"%@ attempting to connect to \\\"%@:%i\\\"\", [self class], _host, (int)_port);\n  _generation += 1;\n  NSUInteger lastGeneration = _generation;\n  [self.connectionClass connectAsynchronouslyToHost:_host\n                                               port:_port\n                                            timeout:_connectionTimeout\n                                         completion:^(GCDTCPConnection* connection) {\n                                           if (connection) {\n                                             if (lastGeneration == _generation) {\n                                               [self willOpenConnection:(GCDTCPPeerConnection*)connection];\n\n                                               dispatch_sync(self.lockQueue, ^{\n                                                 _reconnectionDelay = _minReconnectInterval;\n                                               });\n\n                                             } else {\n                                               _LOG_DEBUG(@\"%@ ignoring stalled connection to \\\"%@:%i\\\"\", [self class], _host, (int)_port);\n                                               [connection close];\n                                             }\n                                           } else if (_automaticallyReconnects) {\n                                             dispatch_sync(self.lockQueue, ^{\n                                               if (_reconnectionDelay > 0.0) {\n                                                 [self _scheduleReconnection];\n                                               }\n                                             });\n                                           }\n                                         }];\n}\n\n- (BOOL)willStart {\n  dispatch_sync(self.lockQueue, ^{\n    _reconnectionDelay = _minReconnectInterval;\n  });\n\n  [self _reconnect];\n\n  return YES;\n}\n\n- (void)didStop {\n  dispatch_sync(self.lockQueue, ^{\n    _reconnectionDelay = 0.0;\n  });\n}\n\n- (void)didCloseConnection:(GCDTCPPeerConnection*)connection {\n  [super didCloseConnection:connection];\n\n  dispatch_sync(self.lockQueue, ^{\n    if (_reconnectionDelay > 0.0) {\n      [self _scheduleReconnection];\n    }\n  });\n}\n\n@end\n\n@implementation GCDTCPClient (Extensions)\n\n- (GCDTCPClientConnection*)connection {\n  return [self.connections anyObject];\n}\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPConnection.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <Foundation/Foundation.h>\n#import <sys/socket.h>\n\n/**\n *  Constants representing the state of a GCDTCPConnection.\n */\ntypedef NS_ENUM(int, GCDTCPConnectionState) {\n  kXLTCPConnectionState_Closed = -1,\n  kXLTCPConnectionState_Initialized = 0,\n  kXLTCPConnectionState_Opened = 1\n};\n\n/**\n *  The GCDTCPConnection is a base class that handles TCP connections.\n */\n@interface GCDTCPConnection : NSObject\n\n/**\n *  Returns the state of the connection.\n */\n@property(nonatomic, readonly) GCDTCPConnectionState state;\n\n/**\n *  Returns the address of the local peer of the connection\n *  as a raw \"struct sockaddr\".\n */\n@property(nonatomic, readonly) NSData* localAddressData;\n\n/**\n *  Returns the address of the remote peer of the connection\n *  as a raw \"struct sockaddr\".\n */\n@property(nonatomic, readonly) NSData* remoteAddressData;\n\n/**\n *  Returns the underlying socket for the connection.\n *\n *  This will be 0 if the connection has been closed.\n *\n *  @warning Do not close the socket directly but use the -close method instead.\n */\n@property(nonatomic, readonly) int socket;\n\n/**\n *  Opens a new connection to a host.\n *\n *  The returned connection will be nil on error.\n */\n+ (void)connectAsynchronouslyToHost:(NSString*)hostname port:(NSUInteger)port timeout:(NSTimeInterval)timeout completion:(void (^)(GCDTCPConnection* connection))completion;\n\n/**\n *  This method is the designated initializer for the class.\n *\n *  @warning The ownership of the socket is transferred to the connection.\n */\n- (instancetype)initWithSocket:(int)socket;\n\n/**\n *  Opens the connection (required before reading or writing from it).\n */\n- (void)open;\n\n/**\n *  Reads data synchronously to the socket.\n *\n *  Pass 0 as \"timeout\" to block indefinitely.\n */\n- (NSData*)readDataWithTimeout:(NSTimeInterval)timeout;\n\n/**\n *  Reads data asynchronously from the socket.\n */\n- (void)readDataAsynchronously:(void (^)(NSData* data))completion;\n\n/**\n *  Writes data synchronously to the socket.\n *\n *  Pass 0 as \"timeout\" to block indefinitely.\n */\n- (BOOL)writeData:(NSData*)data withTimeout:(NSTimeInterval)timeout;\n\n/**\n *  Writes data asynchronously to the socket.\n */\n- (void)writeDataAsynchronously:(NSData*)data completion:(void (^)(BOOL success))completion;\n\n/**\n *  Closes the connection.\n */\n- (void)close;\n\n@end\n\n@interface GCDTCPConnection (Subclassing)\n\n/**\n *  Called after the underlying socket was opened.\n *\n *  The default implementation does nothing.\n */\n- (void)didOpen;\n\n/**\n *  Called after the underlying socket was closed.\n *\n *  The default implementation does nothing.\n */\n- (void)didClose;\n\n@end\n\n@interface GCDTCPConnection (Extensions)\n\n/**\n *  Returns YES if the connection is using IPv6.\n */\n@property(nonatomic, readonly, getter=isUsingIPv6) BOOL usingIPv6;\n\n/**\n *  Returns the port of the local peer of the connection.\n */\n@property(nonatomic, readonly) NSUInteger localPort;\n\n/**\n *  Returns the IP address of the local peer of the connection as a string.\n */\n@property(nonatomic, readonly) NSString* localIPAddress;\n\n/**\n *  Returns the port of the remote peer of the connection.\n */\n@property(nonatomic, readonly) NSUInteger remotePort;\n\n/**\n *  Returns the IP address of the remote peer of the connection as a string.\n */\n@property(nonatomic, readonly) NSString* remoteIPAddress;\n\n/**\n *  Writes a buffer synchronously to the socket.\n */\n- (BOOL)writeBuffer:(const void*)buffer length:(NSUInteger)length withTimeout:(NSTimeInterval)timeout;\n\n/**\n *  Writes a NULL terminated string synchronously to the socket.\n */\n- (BOOL)writeCString:(const char*)string withTimeout:(NSTimeInterval)timeout;\n\n/**\n *  Writes string synchronously to the socket using UTF8 encoding.\n */\n- (BOOL)writeString:(NSString*)string withTimeout:(NSTimeInterval)timeout;\n\n/**\n *  Writes string asynchronously to the socket using UTF8 encoding.\n */\n- (void)writeStringAsynchronously:(NSString*)string completion:(void (^)(BOOL success))completion;\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPConnection.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#if !__has_feature(objc_arc)\n#error GCDNetworking requires ARC\n#endif\n\n#import <net/if.h>\n#import <netdb.h>\n\n#import \"GCDNetworkingPrivate.h\"\n\n#define kReadBufferSize (64 * 1024)  // Max IP packet size\n\ntypedef union {\n  struct sockaddr addr;\n  struct sockaddr_in addr4;\n  struct sockaddr_in6 addr6;\n} SocketAddress;\n\nstatic NSString* _IPAddressFromAddressData(const struct sockaddr* address) {\n  NSString* string = nil;\n  if (address) {\n    char hostBuffer[NI_MAXHOST];\n    if (getnameinfo(address, address->sa_len, hostBuffer, sizeof(hostBuffer), NULL, 0, NI_NUMERICHOST | NI_NOFQDN) >= 0) {\n      string = [NSString stringWithUTF8String:hostBuffer];\n    } else {\n      _LOG_ERROR(@\"Failed converting IP address data to string: %s\", strerror(errno));\n    }\n  }\n  return string;\n}\n\n#pragma clang diagnostic push\n#pragma clang diagnostic ignored \"-Wcast-align\"\n#pragma clang diagnostic ignored \"-Wunreachable-code-return\"\n\nstatic NSUInteger _PortFromAddressData(const struct sockaddr* address) {\n  switch (address->sa_family) {\n    case AF_INET:\n      return ntohs(((const struct sockaddr_in*)address)->sin_port);\n    case AF_INET6:\n      return ntohs(((const struct sockaddr_in6*)address)->sin6_port);\n  }\n  _LOG_DEBUG_UNREACHABLE();\n  return 0;\n}\n\n#pragma clang diagnostic pop\n\n@interface GCDTCPConnection () {\n@private\n  dispatch_queue_t _lockQueue;\n  GCDTCPConnectionState _state;\n  dispatch_group_t _writeGroup;\n}\n@end\n\n@implementation GCDTCPConnection\n\nstatic int _CreateConnectedSocket(NSString* hostname, NSUInteger port, const struct sockaddr* addr, socklen_t len, NSTimeInterval timeout, BOOL isIPv6) {\n  int connectedSocket = socket(isIPv6 ? PF_INET6 : PF_INET, SOCK_STREAM, IPPROTO_TCP);\n  if (connectedSocket >= 0) {\n    BOOL success = NO;\n    fcntl(connectedSocket, F_SETFL, O_NONBLOCK);\n\n    _LOG_DEBUG(@\"Connecting %s socket to \\\"%@:%i\\\" (%@)...\", isIPv6 ? \"IPv6\" : \"IPv4\", hostname, (int)port, _IPAddressFromAddressData(addr));\n    int result = connect(connectedSocket, addr, len);\n    if ((result == -1) && (errno == EINPROGRESS)) {\n      fd_set fdset;\n      FD_ZERO(&fdset);\n      FD_SET(connectedSocket, &fdset);\n      struct timeval tv;\n      tv.tv_sec = timeout;\n      tv.tv_usec = fmod(timeout * 1000000.0, 1.0);\n      result = select(connectedSocket + 1, NULL, &fdset, NULL, &tv);\n      if (result == 1) {\n        int error;\n        socklen_t errorlen = sizeof(error);\n        result = getsockopt(connectedSocket, SOL_SOCKET, SO_ERROR, &error, &errorlen);\n        if (result == 0) {\n          if (error == 0) {\n            success = YES;\n          } else {\n            _LOG_ERROR(@\"Failed connecting %s socket to \\\"%@:%i\\\" (%@): %s\", isIPv6 ? \"IPv6\" : \"IPv4\", hostname, (int)port, _IPAddressFromAddressData(addr), strerror(error));\n          }\n        } else {\n          _LOG_ERROR(@\"Failed retrieving %s socket option: %s\", isIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n        }\n\n      } else if (result == 0) {\n        _LOG_ERROR(@\"Timed out connecting %s socket to \\\"%@:%i\\\" (%@)\", isIPv6 ? \"IPv6\" : \"IPv4\", hostname, (int)port, _IPAddressFromAddressData(addr));\n      }\n    } else {\n      _LOG_ERROR(@\"Failed connecting %s socket to \\\"%@:%i\\\" (%@): %s\", isIPv6 ? \"IPv6\" : \"IPv4\", hostname, (int)port, _IPAddressFromAddressData(addr), strerror(errno));\n    }\n\n    if (success) {\n      fcntl(connectedSocket, F_SETFL, 0);\n    } else {\n      close(connectedSocket);\n      connectedSocket = -1;\n    }\n  } else {\n    _LOG_ERROR(@\"Failed creating %s socket: %s\", isIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n  }\n  return connectedSocket;\n}\n\n+ (void)connectAsynchronouslyToHost:(NSString*)hostname port:(NSUInteger)port timeout:(NSTimeInterval)timeout completion:(void (^)(GCDTCPConnection* connection))completion {\n  dispatch_async(GN_GLOBAL_DISPATCH_QUEUE, ^{\n    GCDTCPConnection* connection = nil;\n\n    CFHostRef host = CFHostCreateWithName(kCFAllocatorDefault, (__bridge CFStringRef)hostname);  // Consider using low-level getaddrinfo() instead\n    CFStreamError error = {0};\n    if (CFHostStartInfoResolution(host, kCFHostAddresses, &error)) {\n      NSArray* addressing = (__bridge NSArray*)CFHostGetAddressing(host, NULL);\n      for (NSData* addressData in addressing) {\n        SocketAddress address;\n        bcopy(addressData.bytes, &address, addressData.length);\n        if (((address.addr.sa_family == AF_INET) && (address.addr.sa_len == sizeof(struct sockaddr_in)))  // Allow IPv4 hosts\n            || ((address.addr.sa_family == AF_INET6) && (address.addr.sa_len == sizeof(struct sockaddr_in6)))) {  // Allow IPv6 hosts\n\n          if (address.addr.sa_family == AF_INET6) {\n            address.addr6.sin6_port = htons(port);\n          } else {\n            address.addr4.sin_port = htons(port);\n          }\n          int socket = _CreateConnectedSocket(hostname, port, &address.addr, address.addr.sa_len, timeout, address.addr.sa_family == AF_INET6);\n          if (socket >= 0) {\n            connection = [[self alloc] initWithSocket:socket];\n            if (connection) {\n              break;\n            } else {\n              _LOG_ERROR(@\"Failed creating %@ instance with connected socket\", NSStringFromClass([self class]));\n              close(socket);\n            }\n          }\n        }\n      }\n    } else {\n      _LOG_ERROR(@\"Failed resolving host \\\"%@\\\": (%i, %i)\", hostname, (int)error.domain, (int)error.error);\n    }\n    CFRelease(host);\n\n    completion(connection);\n  });\n}\n\n- (void)_setSocketOption:(int)option valuePtr:(const void*)valuePtr valueLength:(socklen_t)valueLength {\n  if (setsockopt(_socket, SOL_SOCKET, option, valuePtr, valueLength)) {\n    _LOG_ERROR(@\"Failed setting socket option: %s\", strerror(errno));\n  }\n}\n\n- (void)_setSocketOption:(int)option withIntValue:(int)value {\n  [self _setSocketOption:option valuePtr:&value valueLength:sizeof(int)];\n}\n\n- (id)init {\n  [self doesNotRecognizeSelector:_cmd];\n  return nil;\n}\n\n- (instancetype)initWithSocket:(int)socket {\n  _LOG_DEBUG_CHECK(socket >= 0);\n  if ((self = [super init])) {\n    _lockQueue = dispatch_queue_create(GN_QUEUE_LABEL, DISPATCH_QUEUE_SERIAL);\n    _state = kXLTCPConnectionState_Initialized;\n    _socket = socket;\n\n    [self _setSocketOption:SO_NOSIGPIPE withIntValue:1];  // Make sure this socket cannot generate SIG_PIPE when closed\n    [self _setSocketOption:SO_KEEPALIVE withIntValue:1];  // Enable TCP keep-alive\n\n    struct sockaddr_storage localSockAddr;\n    socklen_t localAddrLen = sizeof(localSockAddr);\n    if (getsockname(_socket, (struct sockaddr*)&localSockAddr, &localAddrLen) == 0) {\n      _localAddressData = [[NSData alloc] initWithBytes:&localSockAddr length:localAddrLen];\n    } else {\n      _LOG_ERROR(@\"Failed retrieving local socket address: %s\", strerror(errno));\n    }\n\n    struct sockaddr_storage remoteSockAddr;\n    socklen_t remoteAddrLen = sizeof(remoteSockAddr);\n    if (getpeername(_socket, (struct sockaddr*)&remoteSockAddr, &remoteAddrLen) == 0) {\n      _remoteAddressData = [[NSData alloc] initWithBytes:&remoteSockAddr length:remoteAddrLen];\n    } else {\n      _LOG_ERROR(@\"Failed retrieving remote socket address: %s\", strerror(errno));\n    }\n  }\n  return self;\n}\n\n- (void)dealloc {\n  if (_socket >= 0) {\n    close(_socket);\n  }\n  if (_state == kXLTCPConnectionState_Opened) {\n    _state = kXLTCPConnectionState_Closed;\n    [self didClose];\n  }\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n  dispatch_release(_lockQueue);\n#endif\n}\n\n- (GCDTCPConnectionState)state {\n  __block GCDTCPConnectionState state;\n  dispatch_sync(_lockQueue, ^{\n    state = _state;\n  });\n  return state;\n}\n\n- (void)open {\n  __block BOOL didOpen = NO;\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Initialized) {\n      _state = kXLTCPConnectionState_Opened;\n      didOpen = YES;\n    }\n  });\n  if (didOpen) {\n    [self didOpen];\n  }\n}\n\n- (NSData*)readDataWithTimeout:(NSTimeInterval)timeout {\n  __block NSMutableData* data = nil;\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Opened) {\n      struct timeval tv;\n      tv.tv_sec = timeout;\n      tv.tv_usec = fmod(timeout * 1000000.0, 1.0);\n      [self _setSocketOption:SO_RCVTIMEO valuePtr:&tv valueLength:sizeof(tv)];\n\n      data = [[NSMutableData alloc] initWithLength:kReadBufferSize];\n      ssize_t len = recv(_socket, data.mutableBytes, data.length, 0);\n      if (len >= 0) {\n        data.length = len;\n      } else {\n        if (errno != EAGAIN) {\n          _LOG_ERROR(@\"Failed reading synchronously from socket: %s\", strerror(errno));\n        }\n        data = nil;\n      }\n    }\n  });\n  return data;\n}\n\n- (void)_readBufferAsynchronously:(void (^)(dispatch_data_t buffer))completion {\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Opened) {\n      dispatch_read(_socket, SIZE_MAX, GN_GLOBAL_DISPATCH_QUEUE, ^(dispatch_data_t data, int error) {\n        @autoreleasepool {\n          if (error) {\n            _LOG_ERROR(@\"Failed reading asynchronously from socket: %s\", strerror(error));\n            if (completion) {\n              completion(NULL);\n            }\n          } else if (completion) {\n            completion(data);\n          }\n        }\n      });\n    } else if (completion) {\n      dispatch_async(GN_GLOBAL_DISPATCH_QUEUE, ^{\n        @autoreleasepool {\n          completion(NULL);\n        }\n      });\n    }\n  });\n}\n\n- (void)readDataAsynchronously:(void (^)(NSData* data))completion {\n  [self _readBufferAsynchronously:^(dispatch_data_t buffer) {\n    if (buffer) {\n      NSMutableData* data = [[NSMutableData alloc] init];\n      dispatch_data_apply(buffer, ^bool(dispatch_data_t region, size_t offset, const void* bytes, size_t length) {\n        [data appendBytes:bytes length:length];\n        return true;\n      });\n      completion(data);\n    } else {\n      completion(nil);\n    }\n  }];\n}\n\n- (BOOL)_writeBytes:(const void*)bytes length:(size_t)length withTimeout:(NSTimeInterval)timeout {\n  __block BOOL result = NO;\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Opened) {\n      struct timeval tv;\n      tv.tv_sec = timeout;\n      tv.tv_usec = fmod(timeout * 1000000.0, 1.0);\n      [self _setSocketOption:SO_SNDTIMEO valuePtr:&tv valueLength:sizeof(tv)];\n\n      ssize_t len = send(_socket, bytes, length, 0);\n      if (len == (ssize_t)length) {\n        result = YES;\n      } else if (errno != EAGAIN) {\n        _LOG_ERROR(@\"Failed writing synchronously to socket: %s\", strerror(errno));\n      }\n    }\n  });\n  return result;\n}\n\n- (BOOL)writeData:(NSData*)data withTimeout:(NSTimeInterval)timeout {\n  return [self _writeBytes:data.bytes length:data.length withTimeout:timeout];\n}\n\n- (void)_writeBufferAsynchronously:(dispatch_data_t)buffer completion:(void (^)(BOOL success))completion {\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Opened) {\n      dispatch_write(_socket, buffer, GN_GLOBAL_DISPATCH_QUEUE, ^(dispatch_data_t data, int error) {\n        @autoreleasepool {\n          if (error) {\n            if (error != EPIPE) {\n              _LOG_ERROR(@\"Failed writing asynchronously to socket: %s\", strerror(error));\n            }\n            if (completion) {\n              completion(NO);\n            }\n          } else if (completion) {\n            completion(YES);\n          }\n        }\n      });\n    } else if (completion) {\n      dispatch_async(GN_GLOBAL_DISPATCH_QUEUE, ^{\n        @autoreleasepool {\n          completion(NO);\n        }\n      });\n    }\n  });\n}\n\n- (void)writeDataAsynchronously:(NSData*)data completion:(void (^)(BOOL success))completion {\n  dispatch_data_t buffer = dispatch_data_create(data.bytes, data.length, GN_GLOBAL_DISPATCH_QUEUE, ^{\n    [data self];  // Keeps ARC from releasing data too early\n  });\n  [self _writeBufferAsynchronously:buffer completion:completion];\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n  dispatch_release(buffer);\n#endif\n}\n\n- (void)close {\n  __block BOOL didClose = NO;\n  dispatch_sync(_lockQueue, ^{\n    if (_state == kXLTCPConnectionState_Opened) {\n      close(_socket);\n      _socket = -1;\n      _state = kXLTCPConnectionState_Closed;\n      didClose = YES;\n    }\n  });\n  if (didClose) {\n    [self didClose];\n  }\n}\n\n@end\n\n@implementation GCDTCPConnection (Subclassing)\n\n- (void)didOpen {\n  _LOG_DEBUG(@\"%@ did open over %s from %@ (%i) to %@ (%i)\", [self class], self.usingIPv6 ? \"IPv6\" : \"IPv4\", self.localIPAddress, (int)self.localPort, self.remoteIPAddress, (int)self.remotePort);\n}\n\n- (void)didClose {\n  _LOG_DEBUG(@\"%@ did close over %s from %@ (%i) to %@ (%i)\", [self class], self.usingIPv6 ? \"IPv6\" : \"IPv4\", self.localIPAddress, (int)self.localPort, self.remoteIPAddress, (int)self.remotePort);\n}\n\n@end\n\n@implementation GCDTCPConnection (Extensions)\n\n- (BOOL)isUsingIPv6 {\n  const struct sockaddr* localSockAddr = _localAddressData.bytes;\n  return (localSockAddr->sa_family == AF_INET6);\n}\n\n- (NSUInteger)localPort {\n  return _PortFromAddressData(_localAddressData.bytes);\n}\n\n- (NSString*)localIPAddress {\n  return _IPAddressFromAddressData(_localAddressData.bytes);\n}\n\n- (NSUInteger)remotePort {\n  return _PortFromAddressData(_remoteAddressData.bytes);\n}\n\n- (NSString*)remoteIPAddress {\n  return _IPAddressFromAddressData(_remoteAddressData.bytes);\n}\n\n- (BOOL)writeBuffer:(const void*)buffer length:(NSUInteger)length withTimeout:(NSTimeInterval)timeout {\n  return [self _writeBytes:buffer length:length withTimeout:timeout];\n}\n\n- (BOOL)writeCString:(const char*)string withTimeout:(NSTimeInterval)timeout {\n  return [self _writeBytes:string length:strlen(string) withTimeout:timeout];\n}\n\n- (BOOL)writeString:(NSString*)string withTimeout:(NSTimeInterval)timeout {\n  return [self writeData:[string dataUsingEncoding:NSUTF8StringEncoding] withTimeout:timeout];\n}\n\n- (void)writeStringAsynchronously:(NSString*)string completion:(void (^)(BOOL success))completion {\n  [self writeDataAsynchronously:[string dataUsingEncoding:NSUTF8StringEncoding] completion:completion];\n}\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPPeer.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTCPConnection.h\"\n\n@class GCDTCPPeer;\n\n/**\n *  The GCDTCPPeerConnection is an abstract class to implement connections\n *  for GCDTCPPeer: it cannot be used directly.\n */\n@interface GCDTCPPeerConnection : GCDTCPConnection\n\n/**\n *  Returns the GCDTCPPeer that owns the connection.\n *\n *  @warning This returns nil after the connection has been closed.\n */\n@property(nonatomic, assign, readonly) GCDTCPPeer* peer;\n\n@end\n\n/**\n *  The GCDTCPPeer is an abstract class to implement TCP peers: it cannot be\n *  used directly.\n */\n@interface GCDTCPPeer : NSObject\n\n/**\n *  Returns the connection class as specified when the peer was initialized.\n */\n@property(nonatomic, readonly) Class connectionClass;\n\n/**\n *  Returns YES if the peer is running.\n */\n@property(nonatomic, readonly, getter=isRunning) BOOL running;\n\n/**\n *  Returns all currently opened connections.\n */\n@property(nonatomic, readonly) NSSet* connections;\n\n#if TARGET_OS_IPHONE\n/**\n *  Sets if the peer automatically stops and starts while entering background\n *  and foreground on iOS.\n *\n *  When an app enters background on iOS and is suspended, it cannot leave\n *  listening sockets open, so it must either close them or start a background\n *  task to prevent the app from getting suspended while in background.\n *\n *  If this property is set to NO then the peer will automatically create a\n *  background task when it is started and end it when it is stopped. Note that\n *  this task can only run for a limited time while the app is in background\n *  before iOS eventually force ends it. At this point the peer will be stopped\n *  no matter what.\n *\n *  The default value is NO.\n */\n@property(nonatomic) BOOL suspendInBackground;\n#endif\n\n/**\n *  This method is the designated initializer for the class.\n *\n *  Connection class must be [GCDTCPPeerConnection class] or a subclass of it.\n */\n- (instancetype)initWithConnectionClass:(Class)connectionClass;\n\n/**\n *  Starts the peer.\n *\n *  Returns NO on error.\n */\n- (BOOL)start;\n\n/**\n *  Stops the peer.\n *\n *  @warning This blocks until all opened connections have been closed.\n */\n- (void)stop;\n\n@end\n\n@interface GCDTCPPeer (Subclassing)\n\n/**\n *  Returns a GCD serial queue subclasses can use to protect internal data\n *  that can be accessed concurrently from multiple threads.\n */\n@property(nonatomic, readonly) dispatch_queue_t lockQueue;\n\n/**\n *  This method is called whenever the peer starts.\n *\n *  @warning This method can be called on arbitrary threads.\n */\n- (BOOL)willStart;\n\n/**\n *  This method is called whenever a new connection is opened.\n *\n *  @warning This method can be called on arbitrary threads.\n */\n- (void)willOpenConnection:(GCDTCPPeerConnection*)connection;\n\n/**\n *  This method is called after a connection has been closed.\n *\n *  @warning This method can be called on arbitrary threads.\n */\n- (void)didCloseConnection:(GCDTCPPeerConnection*)connection;\n\n/**\n *  This method is called whenever the peer stops.\n *\n *  @warning This method can be called on arbitrary threads.\n */\n- (void)didStop;\n\n@end\n\n@interface GCDTCPPeer (Extensions)\n\n/**\n *  Enumerates all currently opened connections.\n */\n- (void)enumerateConnectionsUsingBlock:(void (^)(GCDTCPPeerConnection* connection, BOOL* stop))block;\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPPeer.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#if !__has_feature(objc_arc)\n#error GCDNetworking requires ARC\n#endif\n\n#import <TargetConditionals.h>\n#if TARGET_OS_IPHONE\n#import <UIKit/UIKit.h>\n#endif\n\n#import \"GCDNetworkingPrivate.h\"\n\n@interface GCDTCPPeerConnection ()\n@property(nonatomic, assign) GCDTCPPeer* peer;\n@end\n\n@implementation GCDTCPPeerConnection\n\n- (void)didClose {\n  [super didClose];\n\n  [_peer didCloseConnection:self];\n  _peer = nil;\n}\n\n@end\n\n@interface GCDTCPPeer () {\n@private\n  dispatch_queue_t _lockQueue;\n  dispatch_group_t _syncGroup;\n  NSMutableSet* _connections;\n#if TARGET_OS_IPHONE\n  UIBackgroundTaskIdentifier _backgroundTask;\n  BOOL _restart;\n#endif\n}\n@end\n\n@implementation GCDTCPPeer\n\n- (id)init {\n  [self doesNotRecognizeSelector:_cmd];\n  return nil;\n}\n\n- (instancetype)initWithConnectionClass:(Class)connectionClass {\n  _LOG_DEBUG_CHECK([connectionClass isSubclassOfClass:[GCDTCPPeerConnection class]]);\n  if ((self = [super init])) {\n    _connectionClass = connectionClass;\n\n    _lockQueue = dispatch_queue_create(GN_QUEUE_LABEL, DISPATCH_QUEUE_SERIAL);\n    _syncGroup = dispatch_group_create();\n    _connections = [[NSMutableSet alloc] init];\n#if TARGET_OS_IPHONE\n    _backgroundTask = UIBackgroundTaskInvalid;\n#endif\n\n#if TARGET_OS_IPHONE\n    [[NSNotificationCenter defaultCenter] addObserver:self\n                                             selector:@selector(_didEnterBackground:)\n                                                 name:UIApplicationDidEnterBackgroundNotification\n                                               object:nil];\n    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_willEnterForeground:) name:UIApplicationWillEnterForegroundNotification object:nil];\n#endif\n  }\n  return self;\n}\n\n- (void)dealloc {\n#if TARGET_OS_IPHONE\n  [[NSNotificationCenter defaultCenter] removeObserver:self\n                                                  name:UIApplicationDidEnterBackgroundNotification\n                                                object:nil];\n  [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationWillEnterForegroundNotification object:nil];\n#endif\n\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n  dispatch_release(_syncGroup);\n  dispatch_release(_lockQueue);\n#endif\n}\n\n- (NSSet*)connections {\n  __block NSSet* connections;\n  dispatch_sync(_lockQueue, ^{\n    connections = [_connections copy];\n  });\n  return connections;\n}\n\n- (BOOL)start {\n  _LOG_DEBUG_CHECK(!_running);\n\n  if (![self willStart]) {\n    return NO;\n  }\n\n#if TARGET_OS_IPHONE\n  if (!_suspendInBackground) {\n    _backgroundTask = [[UIApplication sharedApplication] beginBackgroundTaskWithExpirationHandler:^{\n      [self stop];\n      _restart = YES;\n\n      [[UIApplication sharedApplication] endBackgroundTask:_backgroundTask];\n      _backgroundTask = UIBackgroundTaskInvalid;\n    }];\n  }\n  _restart = NO;\n#endif\n\n  _running = YES;\n  _LOG_DEBUG(@\"%@ started\", [self class]);\n  return YES;\n}\n\n#if TARGET_OS_IPHONE\n\n- (void)_didEnterBackground:(NSNotification*)notification {\n  if (_running && _suspendInBackground) {\n    [self stop];\n    _restart = YES;\n  }\n}\n\n- (void)_willEnterForeground:(NSNotification*)notification {\n  if (_restart) {\n    [self start];  // Not much we can do on failure\n  }\n}\n\n#endif\n\n- (void)stop {\n  _LOG_DEBUG_CHECK(_running);\n\n#if TARGET_OS_IPHONE\n  if (_backgroundTask != UIBackgroundTaskInvalid) {\n    [[UIApplication sharedApplication] endBackgroundTask:_backgroundTask];\n    _backgroundTask = UIBackgroundTaskInvalid;\n  }\n#endif\n\n  [self didStop];\n\n  NSSet* connections = self.connections;\n  for (GCDTCPPeerConnection* connection in connections) {  // No need to use \"_lockQueue\" since no new connections can be created anymore and it would deadlock with -didCloseConnection:\n    [connection close];\n  }\n  dispatch_group_wait(_syncGroup, DISPATCH_TIME_FOREVER);  // Wait until all connections are closed\n\n  _running = NO;\n  _LOG_DEBUG(@\"%@ stopped\", [self class]);\n}\n\n@end\n\n@implementation GCDTCPPeer (Subclassing)\n\n- (dispatch_queue_t)lockQueue {\n  return _lockQueue;\n}\n\n- (BOOL)willStart {\n  return YES;\n}\n\n- (void)didStop {\n  ;\n}\n\n- (void)willOpenConnection:(GCDTCPPeerConnection*)connection {\n  _LOG_DEBUG(@\"%@ did connect to peer at \\\"%@\\\" (%i)\", [self class], connection.remoteIPAddress, (int)connection.remotePort);\n  connection.peer = self;\n  dispatch_sync(_lockQueue, ^{\n    dispatch_group_enter(_syncGroup);\n    [_connections addObject:connection];\n  });\n  [connection open];\n}\n\n- (void)didCloseConnection:(GCDTCPPeerConnection*)connection {\n  dispatch_sync(_lockQueue, ^{\n    if ([_connections containsObject:connection]) {\n      [_connections removeObject:connection];\n      dispatch_group_leave(_syncGroup);\n    }\n  });\n  _LOG_DEBUG(@\"%@ did disconnect from peer at \\\"%@\\\" (%i)\", [self class], connection.remoteIPAddress, (int)connection.remotePort);\n}\n\n@end\n\n@implementation GCDTCPPeer (Extensions)\n\n- (void)enumerateConnectionsUsingBlock:(void (^)(GCDTCPPeerConnection* connection, BOOL* stop))block {\n  dispatch_sync(_lockQueue, ^{\n    BOOL stop = NO;\n    for (GCDTCPPeerConnection* connection in _connections) {\n      block(connection, &stop);\n      if (stop) {\n        break;\n      }\n    }\n  });\n}\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPServer.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTCPPeer.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n *  On OS X, returns the IPv4 or IPv6 address as a string of the primary\n *  connected service or nil if not available.\n *  \n *  On iOS, returns the IPv4 or IPv6 address as a string of the WiFi\n *  interface if connected or nil otherwise.\n */\nNSString* GCDTCPServerGetPrimaryIPAddress(BOOL useIPv6);\n\n#ifdef __cplusplus\n}\n#endif\n\n@class GCDTCPServer;\n\n/**\n *  The GCDTCPServerConnection is an abstract class to implement connections\n *  for GCDTCPServer: it cannot be used directly.\n */\n@interface GCDTCPServerConnection : GCDTCPPeerConnection\n@end\n\n/**\n *  The GCDTCPServer is a base class that implements a TCP server. It listens for\n *  IPv4 or IPv6 TCP connections on a port and then creates GCDTCPServerConnection\n *  instances for each.\n *\n *  @warning On iOS, connecting to the server will not work while your app has\n *  been suspended by the OS while in background.\n */\n@interface GCDTCPServer : GCDTCPPeer\n\n/**\n *  Returns the port as specified when the server was initialized.\n */\n@property(nonatomic, readonly) NSUInteger port;\n\n/**\n *  This method is the designated initializer for the class.\n *\n *  Connection class must be [GCDTCPServerConnection class] or a subclass of it.\n */\n- (instancetype)initWithConnectionClass:(Class)connectionClass port:(NSUInteger)port;\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking/GCDTCPServer.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#if !__has_feature(objc_arc)\n#error GCDNetworking requires ARC\n#endif\n\n#import <TargetConditionals.h>\n#if TARGET_OS_IPHONE\n#import <MobileCoreServices/MobileCoreServices.h>\n#else\n#import <SystemConfiguration/SystemConfiguration.h>\n#endif\n#import <ifaddrs.h>\n#import <net/if.h>\n#import <netdb.h>\n\n#import \"GCDNetworkingPrivate.h\"\n\n#define kMaxPendingConnections 4\n\nstatic NSString* _StringFromSockAddr(const struct sockaddr* addr, BOOL includeService) {\n  NSString* string = nil;\n  char hostBuffer[NI_MAXHOST];\n  char serviceBuffer[NI_MAXSERV];\n  if (getnameinfo(addr, addr->sa_len, hostBuffer, sizeof(hostBuffer), serviceBuffer, sizeof(serviceBuffer), NI_NUMERICHOST | NI_NUMERICSERV | NI_NOFQDN) >= 0) {\n    string = includeService ? [NSString stringWithFormat:@\"%s:%s\", hostBuffer, serviceBuffer] : [NSString stringWithUTF8String:hostBuffer];\n  } else {\n    _LOG_DEBUG_UNREACHABLE();\n  }\n  return string;\n}\n\nNSString* GCDTCPServerGetPrimaryIPAddress(BOOL useIPv6) {\n  NSString* address = nil;\n#if TARGET_OS_IPHONE\n#if !TARGET_IPHONE_SIMULATOR\n  const char* primaryInterface = \"en0\";  // WiFi interface on iOS\n#endif\n#else\n  const char* primaryInterface = NULL;\n  SCDynamicStoreRef store = SCDynamicStoreCreate(kCFAllocatorDefault, CFSTR(\"XLTCPServer\"), NULL, NULL);\n  if (store) {\n    CFPropertyListRef info = SCDynamicStoreCopyValue(store, CFSTR(\"State:/Network/Global/IPv4\"));  // There is no equivalent for IPv6 but the primary interface should be the same\n    if (info) {\n      primaryInterface = [[NSString stringWithString:(id)[(__bridge NSDictionary*)info objectForKey:@\"PrimaryInterface\"]] UTF8String];\n      CFRelease(info);\n    }\n    CFRelease(store);\n  }\n  if (primaryInterface == NULL) {\n    primaryInterface = \"lo0\";\n  }\n#endif\n  struct ifaddrs* list;\n  if (getifaddrs(&list) >= 0) {\n    for (struct ifaddrs* ifap = list; ifap; ifap = ifap->ifa_next) {\n#if TARGET_IPHONE_SIMULATOR\n      // Assume en0 is Ethernet and en1 is WiFi since there is no way to use SystemConfiguration framework in iOS Simulator\n      if (strcmp(ifap->ifa_name, \"en0\") && strcmp(ifap->ifa_name, \"en1\"))\n#else\n      if (strcmp(ifap->ifa_name, primaryInterface))\n#endif\n      {\n        continue;\n      }\n      if ((ifap->ifa_flags & IFF_UP) && ((!useIPv6 && (ifap->ifa_addr->sa_family == AF_INET)) || (useIPv6 && (ifap->ifa_addr->sa_family == AF_INET6)))) {\n        address = _StringFromSockAddr(ifap->ifa_addr, NO);\n        break;\n      }\n    }\n    freeifaddrs(list);\n  }\n  return address;\n}\n\n@implementation GCDTCPServerConnection\n@end\n\n@interface GCDTCPServer () {\n@private\n  dispatch_group_t _sourceGroup;\n  dispatch_source_t _source4;\n  dispatch_source_t _source6;\n}\n@end\n\n@implementation GCDTCPServer\n\n- (instancetype)initWithConnectionClass:(Class)connectionClass port:(NSUInteger)port {\n  _LOG_DEBUG_CHECK([connectionClass isSubclassOfClass:[GCDTCPServerConnection class]]);\n  if ((self = [super initWithConnectionClass:connectionClass])) {\n    _port = port;\n\n    _sourceGroup = dispatch_group_create();\n  }\n  return self;\n}\n\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n\n- (void)dealloc {\n  dispatch_release(_sourceGroup);\n}\n\n#endif\n\n- (int)_createListeningSocket:(BOOL)useIPv6 localAddress:(const void*)address length:(socklen_t)length {\n  int listeningSocket = socket(useIPv6 ? PF_INET6 : PF_INET, SOCK_STREAM, IPPROTO_TCP);\n  if (listeningSocket >= 0) {\n    int yes = 1;\n    setsockopt(listeningSocket, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(yes));\n\n    if (bind(listeningSocket, address, length) == 0) {\n      if (listen(listeningSocket, kMaxPendingConnections) == 0) {\n        return listeningSocket;\n      } else {\n        _LOG_ERROR(@\"Failed starting %s listening socket: %s\", useIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n        close(listeningSocket);\n      }\n    } else {\n      _LOG_ERROR(@\"Failed binding %s listening socket: %s\", useIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n      close(listeningSocket);\n    }\n  } else {\n    _LOG_ERROR(@\"Failed creating %s listening socket: %s\", useIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n  }\n  return -1;\n}\n\n- (dispatch_source_t)_createDispatchSourceWithListeningSocket:(int)listeningSocket isIPv6:(BOOL)isIPv6 {\n  dispatch_group_enter(_sourceGroup);\n  dispatch_source_t source = dispatch_source_create(DISPATCH_SOURCE_TYPE_READ, listeningSocket, 0, GN_GLOBAL_DISPATCH_QUEUE);\n  dispatch_source_set_cancel_handler(source, ^{\n    close(listeningSocket);\n    dispatch_group_leave(_sourceGroup);\n  });\n  dispatch_source_set_event_handler(source, ^{\n    @autoreleasepool {\n      struct sockaddr remoteSockAddr;\n      socklen_t remoteAddrLen = sizeof(remoteSockAddr);\n      int socket = accept(listeningSocket, &remoteSockAddr, &remoteAddrLen);\n      if (socket >= 0) {\n        GCDTCPServerConnection* connection = [[self.connectionClass alloc] initWithSocket:socket];\n        if (connection) {\n          [self willOpenConnection:connection];\n        } else {\n          _LOG_ERROR(@\"Failed creating %@ instance\", NSStringFromClass(self.connectionClass));\n          close(socket);\n        }\n      } else {\n        _LOG_ERROR(@\"Failed accepting %s socket: %s\", isIPv6 ? \"IPv6\" : \"IPv4\", strerror(errno));\n      }\n    }\n  });\n  return source;\n}\n\n- (BOOL)willStart {\n  struct sockaddr_in addr4;\n  bzero(&addr4, sizeof(addr4));\n  addr4.sin_len = sizeof(addr4);\n  addr4.sin_family = AF_INET;\n  addr4.sin_port = htons(_port);\n  addr4.sin_addr.s_addr = htonl(INADDR_ANY);\n  int listeningSocket4 = [self _createListeningSocket:NO localAddress:&addr4 length:sizeof(addr4)];\n\n  struct sockaddr_in6 addr6;\n  bzero(&addr6, sizeof(addr6));\n  addr6.sin6_len = sizeof(addr6);\n  addr6.sin6_family = AF_INET6;\n  addr6.sin6_port = htons(_port);\n  addr6.sin6_addr = in6addr_any;\n  int listeningSocket6 = [self _createListeningSocket:YES localAddress:&addr6 length:sizeof(addr6)];\n\n  if ((listeningSocket4 < 0) || (listeningSocket6 < 0)) {\n    close(listeningSocket4);\n    close(listeningSocket6);\n    return NO;\n  }\n\n  _source4 = [self _createDispatchSourceWithListeningSocket:listeningSocket4 isIPv6:NO];\n  dispatch_resume(_source4);\n\n  _source6 = [self _createDispatchSourceWithListeningSocket:listeningSocket6 isIPv6:YES];\n  dispatch_resume(_source6);\n\n  return YES;\n}\n\n- (void)didStop {\n  dispatch_source_cancel(_source6);\n  dispatch_source_cancel(_source4);\n  dispatch_group_wait(_sourceGroup, DISPATCH_TIME_FOREVER);  // Wait until the cancellation handlers have been called which guarantees the listening sockets are closed\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n  dispatch_release(_source6);\n#endif\n  _source6 = NULL;\n#if !OS_OBJECT_USE_OBJC_RETAIN_RELEASE\n  dispatch_release(_source4);\n#endif\n  _source4 = NULL;\n}\n\n@end\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking.xcodeproj/project.pbxproj",
    "content": "// !$*UTF8*$!\n{\n\tarchiveVersion = 1;\n\tclasses = {\n\t};\n\tobjectVersion = 48;\n\tobjects = {\n\n/* Begin PBXAggregateTarget section */\n\t\tE2B3CEE619E91770003ED065 /* Build All */ = {\n\t\t\tisa = PBXAggregateTarget;\n\t\t\tbuildConfigurationList = E2B3CEE719E91770003ED065 /* Build configuration list for PBXAggregateTarget \"Build All\" */;\n\t\t\tbuildPhases = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t\tE2B3CEEB19E91784003ED065 /* PBXTargetDependency */,\n\t\t\t\tE2B3CF2B19E9189C003ED065 /* PBXTargetDependency */,\n\t\t\t\tE2168F9619EE04B200865350 /* PBXTargetDependency */,\n\t\t\t);\n\t\t\tname = \"Build All\";\n\t\t\tproductName = \"Build All\";\n\t\t};\n/* End PBXAggregateTarget section */\n\n/* Begin PBXBuildFile section */\n\t\tE26ABC2C19EC9F9A00654D9F /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = E26ABC2B19EC9F9A00654D9F /* main.m */; };\n\t\tE280BF1419E9FF5000D85595 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1319E9FF5000D85595 /* CFNetwork.framework */; };\n\t\tE280BF1619E9FF5500D85595 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1519E9FF5500D85595 /* CFNetwork.framework */; };\n\t\tE2812BB919F2E9780046DDC1 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB219F2E9780046DDC1 /* GCDTCPClient.m */; };\n\t\tE2812BBA19F2E9780046DDC1 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB219F2E9780046DDC1 /* GCDTCPClient.m */; };\n\t\tE2812BBC19F2E9780046DDC1 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB219F2E9780046DDC1 /* GCDTCPClient.m */; };\n\t\tE2812BBD19F2E9780046DDC1 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB419F2E9780046DDC1 /* GCDTCPConnection.m */; };\n\t\tE2812BBE19F2E9780046DDC1 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB419F2E9780046DDC1 /* GCDTCPConnection.m */; };\n\t\tE2812BC019F2E9780046DDC1 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB419F2E9780046DDC1 /* GCDTCPConnection.m */; };\n\t\tE2812BC119F2E9780046DDC1 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB619F2E9780046DDC1 /* GCDTCPPeer.m */; };\n\t\tE2812BC219F2E9780046DDC1 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB619F2E9780046DDC1 /* GCDTCPPeer.m */; };\n\t\tE2812BC419F2E9780046DDC1 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB619F2E9780046DDC1 /* GCDTCPPeer.m */; };\n\t\tE2812BC519F2E9780046DDC1 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB819F2E9780046DDC1 /* GCDTCPServer.m */; };\n\t\tE2812BC619F2E9780046DDC1 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB819F2E9780046DDC1 /* GCDTCPServer.m */; };\n\t\tE2812BC819F2E9780046DDC1 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2812BB819F2E9780046DDC1 /* GCDTCPServer.m */; };\n\t\tE295AF8C1E6B4B1F00EAC2FF /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E295AF8B1E6B4B1F00EAC2FF /* SystemConfiguration.framework */; };\n\t\tE295AF8D1E6B4B5C00EAC2FF /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E295AF8B1E6B4B1F00EAC2FF /* SystemConfiguration.framework */; };\n\t\tE298C47A19ED866100C76821 /* GCDNetworking_Tests.m in Sources */ = {isa = PBXBuildFile; fileRef = E298C47919ED866100C76821 /* GCDNetworking_Tests.m */; };\n\t\tE298C48619ED892500C76821 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1319E9FF5000D85595 /* CFNetwork.framework */; };\n\t\tE2B3CF1B19E91825003ED065 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B3CF1819E91825003ED065 /* AppDelegate.m */; };\n\t\tE2B3CF1D19E91825003ED065 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B3CF1A19E91825003ED065 /* main.m */; };\n\t\tE2B3CF3019E919DD003ED065 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E2B3CF2F19E919DD003ED065 /* UIKit.framework */; };\n/* End PBXBuildFile section */\n\n/* Begin PBXContainerItemProxy section */\n\t\tE2168F9519EE04B200865350 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E298C46B19ED859F00C76821;\n\t\t\tremoteInfo = \"XLFacility (Tests)\";\n\t\t};\n\t\tE2B3CEEA19E91784003ED065 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E26DC16619E8494700C68DDC;\n\t\t\tremoteInfo = GCDLogger;\n\t\t};\n\t\tE2B3CF2A19E9189C003ED065 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E2B3CEEF19E917BB003ED065;\n\t\t\tremoteInfo = \"GCDLogger (iOS)\";\n\t\t};\n/* End PBXContainerItemProxy section */\n\n/* Begin PBXFileReference section */\n\t\tE22E917A19F2EBD40043457E /* GCDNetworkingPrivate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GCDNetworkingPrivate.h; sourceTree = \"<group>\"; };\n\t\tE22E917F19F2F0850043457E /* GCDNetworking.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GCDNetworking.h; sourceTree = \"<group>\"; };\n\t\tE26ABC2B19EC9F9A00654D9F /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = \"<group>\"; };\n\t\tE26DC16719E8494700C68DDC /* GCDNetworking */ = {isa = PBXFileReference; explicitFileType = \"compiled.mach-o.executable\"; includeInIndex = 0; path = GCDNetworking; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE280BF0E19E9F3DF00D85595 /* README.md */ = {isa = PBXFileReference; lastKnownFileType = net.daringfireball.markdown; path = README.md; sourceTree = \"<group>\"; };\n\t\tE280BF1319E9FF5000D85595 /* CFNetwork.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CFNetwork.framework; path = System/Library/Frameworks/CFNetwork.framework; sourceTree = SDKROOT; };\n\t\tE280BF1519E9FF5500D85595 /* CFNetwork.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CFNetwork.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS8.1.sdk/System/Library/Frameworks/CFNetwork.framework; sourceTree = DEVELOPER_DIR; };\n\t\tE2812BB119F2E9780046DDC1 /* GCDTCPClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPClient.h; sourceTree = \"<group>\"; };\n\t\tE2812BB219F2E9780046DDC1 /* GCDTCPClient.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPClient.m; sourceTree = \"<group>\"; };\n\t\tE2812BB319F2E9780046DDC1 /* GCDTCPConnection.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPConnection.h; sourceTree = \"<group>\"; };\n\t\tE2812BB419F2E9780046DDC1 /* GCDTCPConnection.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPConnection.m; sourceTree = \"<group>\"; };\n\t\tE2812BB519F2E9780046DDC1 /* GCDTCPPeer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPPeer.h; sourceTree = \"<group>\"; };\n\t\tE2812BB619F2E9780046DDC1 /* GCDTCPPeer.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPPeer.m; sourceTree = \"<group>\"; };\n\t\tE2812BB719F2E9780046DDC1 /* GCDTCPServer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPServer.h; sourceTree = \"<group>\"; };\n\t\tE2812BB819F2E9780046DDC1 /* GCDTCPServer.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPServer.m; sourceTree = \"<group>\"; };\n\t\tE295AF8B1E6B4B1F00EAC2FF /* SystemConfiguration.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SystemConfiguration.framework; path = System/Library/Frameworks/SystemConfiguration.framework; sourceTree = SDKROOT; };\n\t\tE298C46C19ED859F00C76821 /* Tests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = Tests.xctest; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE298C47919ED866100C76821 /* GCDNetworking_Tests.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDNetworking_Tests.m; sourceTree = \"<group>\"; };\n\t\tE2B03E3A19F493A500D56CA6 /* GCDNetworkingLoggingBridgePrivate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GCDNetworkingLoggingBridgePrivate.h; sourceTree = \"<group>\"; };\n\t\tE2B3CEF019E917BB003ED065 /* GCDNetworking.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = GCDNetworking.app; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE2B3CF1719E91825003ED065 /* AppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = \"<group>\"; };\n\t\tE2B3CF1819E91825003ED065 /* AppDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = \"<group>\"; };\n\t\tE2B3CF1919E91825003ED065 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = \"<group>\"; };\n\t\tE2B3CF1A19E91825003ED065 /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = \"<group>\"; };\n\t\tE2B3CF2F19E919DD003ED065 /* UIKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = UIKit.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS8.1.sdk/System/Library/Frameworks/UIKit.framework; sourceTree = DEVELOPER_DIR; };\n/* End PBXFileReference section */\n\n/* Begin PBXFrameworksBuildPhase section */\n\t\tE26DC16419E8494700C68DDC /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE295AF8C1E6B4B1F00EAC2FF /* SystemConfiguration.framework in Frameworks */,\n\t\t\t\tE280BF1419E9FF5000D85595 /* CFNetwork.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE298C46919ED859F00C76821 /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE295AF8D1E6B4B5C00EAC2FF /* SystemConfiguration.framework in Frameworks */,\n\t\t\t\tE298C48619ED892500C76821 /* CFNetwork.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE2B3CEED19E917BB003ED065 /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE280BF1619E9FF5500D85595 /* CFNetwork.framework in Frameworks */,\n\t\t\t\tE2B3CF3019E919DD003ED065 /* UIKit.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXFrameworksBuildPhase section */\n\n/* Begin PBXGroup section */\n\t\tE26ABC2A19EC9F9A00654D9F /* CLT */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE26ABC2B19EC9F9A00654D9F /* main.m */,\n\t\t\t);\n\t\t\tpath = CLT;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE26DC15E19E8494700C68DDC = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE280BF0E19E9F3DF00D85595 /* README.md */,\n\t\t\t\tE2812BB019F2E9780046DDC1 /* GCDNetworking */,\n\t\t\t\tE26ABC2A19EC9F9A00654D9F /* CLT */,\n\t\t\t\tE2B3CF1619E91825003ED065 /* iOS */,\n\t\t\t\tE298C47719ED866100C76821 /* Tests */,\n\t\t\t\tE26DC19E19E883CC00C68DDC /* Mac Frameworks and Libraries */,\n\t\t\t\tE2B3CF2E19E919AC003ED065 /* iOS Frameworks and Libraries */,\n\t\t\t\tE26DC16819E8494700C68DDC /* Products */,\n\t\t\t);\n\t\t\tindentWidth = 2;\n\t\t\tsourceTree = \"<group>\";\n\t\t\ttabWidth = 2;\n\t\t};\n\t\tE26DC16819E8494700C68DDC /* Products */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE26DC16719E8494700C68DDC /* GCDNetworking */,\n\t\t\t\tE2B3CEF019E917BB003ED065 /* GCDNetworking.app */,\n\t\t\t\tE298C46C19ED859F00C76821 /* Tests.xctest */,\n\t\t\t);\n\t\t\tname = Products;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE26DC19E19E883CC00C68DDC /* Mac Frameworks and Libraries */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE295AF8B1E6B4B1F00EAC2FF /* SystemConfiguration.framework */,\n\t\t\t\tE280BF1319E9FF5000D85595 /* CFNetwork.framework */,\n\t\t\t);\n\t\t\tname = \"Mac Frameworks and Libraries\";\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2812BB019F2E9780046DDC1 /* GCDNetworking */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE22E917F19F2F0850043457E /* GCDNetworking.h */,\n\t\t\t\tE22E917A19F2EBD40043457E /* GCDNetworkingPrivate.h */,\n\t\t\t\tE2B03E3A19F493A500D56CA6 /* GCDNetworkingLoggingBridgePrivate.h */,\n\t\t\t\tE2812BB119F2E9780046DDC1 /* GCDTCPClient.h */,\n\t\t\t\tE2812BB219F2E9780046DDC1 /* GCDTCPClient.m */,\n\t\t\t\tE2812BB319F2E9780046DDC1 /* GCDTCPConnection.h */,\n\t\t\t\tE2812BB419F2E9780046DDC1 /* GCDTCPConnection.m */,\n\t\t\t\tE2812BB519F2E9780046DDC1 /* GCDTCPPeer.h */,\n\t\t\t\tE2812BB619F2E9780046DDC1 /* GCDTCPPeer.m */,\n\t\t\t\tE2812BB719F2E9780046DDC1 /* GCDTCPServer.h */,\n\t\t\t\tE2812BB819F2E9780046DDC1 /* GCDTCPServer.m */,\n\t\t\t);\n\t\t\tpath = GCDNetworking;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE298C47719ED866100C76821 /* Tests */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE298C47919ED866100C76821 /* GCDNetworking_Tests.m */,\n\t\t\t);\n\t\t\tpath = Tests;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B3CF1619E91825003ED065 /* iOS */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B3CF1719E91825003ED065 /* AppDelegate.h */,\n\t\t\t\tE2B3CF1819E91825003ED065 /* AppDelegate.m */,\n\t\t\t\tE2B3CF1919E91825003ED065 /* Info.plist */,\n\t\t\t\tE2B3CF1A19E91825003ED065 /* main.m */,\n\t\t\t);\n\t\t\tpath = iOS;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B3CF2E19E919AC003ED065 /* iOS Frameworks and Libraries */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B3CF2F19E919DD003ED065 /* UIKit.framework */,\n\t\t\t\tE280BF1519E9FF5500D85595 /* CFNetwork.framework */,\n\t\t\t);\n\t\t\tname = \"iOS Frameworks and Libraries\";\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n/* End PBXGroup section */\n\n/* Begin PBXNativeTarget section */\n\t\tE26DC16619E8494700C68DDC /* GCDNetworking (CLT) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E26DC16E19E8494700C68DDC /* Build configuration list for PBXNativeTarget \"GCDNetworking (CLT)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE26DC16319E8494700C68DDC /* Sources */,\n\t\t\t\tE26DC16419E8494700C68DDC /* Frameworks */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDNetworking (CLT)\";\n\t\t\tproductName = Logger;\n\t\t\tproductReference = E26DC16719E8494700C68DDC /* GCDNetworking */;\n\t\t\tproductType = \"com.apple.product-type.tool\";\n\t\t};\n\t\tE298C46B19ED859F00C76821 /* GCDNetworking (Tests) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E298C47619ED859F00C76821 /* Build configuration list for PBXNativeTarget \"GCDNetworking (Tests)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE298C46819ED859F00C76821 /* Sources */,\n\t\t\t\tE298C46919ED859F00C76821 /* Frameworks */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDNetworking (Tests)\";\n\t\t\tproductName = \"XLFacility Tests\";\n\t\t\tproductReference = E298C46C19ED859F00C76821 /* Tests.xctest */;\n\t\t\tproductType = \"com.apple.product-type.bundle.unit-test\";\n\t\t};\n\t\tE2B3CEEF19E917BB003ED065 /* GCDNetworking (iOS) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E2B3CF1019E917BC003ED065 /* Build configuration list for PBXNativeTarget \"GCDNetworking (iOS)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE2B3CEEC19E917BB003ED065 /* Sources */,\n\t\t\t\tE2B3CEED19E917BB003ED065 /* Frameworks */,\n\t\t\t\tE2B3CEEE19E917BB003ED065 /* Resources */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDNetworking (iOS)\";\n\t\t\tproductName = GCDLogger;\n\t\t\tproductReference = E2B3CEF019E917BB003ED065 /* GCDNetworking.app */;\n\t\t\tproductType = \"com.apple.product-type.application\";\n\t\t};\n/* End PBXNativeTarget section */\n\n/* Begin PBXProject section */\n\t\tE26DC15F19E8494700C68DDC /* Project object */ = {\n\t\t\tisa = PBXProject;\n\t\t\tattributes = {\n\t\t\t\tLastUpgradeCheck = 0830;\n\t\t\t\tORGANIZATIONNAME = \"\";\n\t\t\t\tTargetAttributes = {\n\t\t\t\t\tE26DC16619E8494700C68DDC = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t\tE298C46B19ED859F00C76821 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t\tTestTargetID = E26ABC0919EC9E2D00654D9F;\n\t\t\t\t\t};\n\t\t\t\t\tE2B3CEE619E91770003ED065 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t\tE2B3CEEF19E917BB003ED065 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t};\n\t\t\t};\n\t\t\tbuildConfigurationList = E26DC16219E8494700C68DDC /* Build configuration list for PBXProject \"GCDNetworking\" */;\n\t\t\tcompatibilityVersion = \"Xcode 8.0\";\n\t\t\tdevelopmentRegion = English;\n\t\t\thasScannedForEncodings = 0;\n\t\t\tknownRegions = (\n\t\t\t\ten,\n\t\t\t\tBase,\n\t\t\t);\n\t\t\tmainGroup = E26DC15E19E8494700C68DDC;\n\t\t\tproductRefGroup = E26DC16819E8494700C68DDC /* Products */;\n\t\t\tprojectDirPath = \"\";\n\t\t\tprojectRoot = \"\";\n\t\t\ttargets = (\n\t\t\t\tE2B3CEE619E91770003ED065 /* Build All */,\n\t\t\t\tE26DC16619E8494700C68DDC /* GCDNetworking (CLT) */,\n\t\t\t\tE2B3CEEF19E917BB003ED065 /* GCDNetworking (iOS) */,\n\t\t\t\tE298C46B19ED859F00C76821 /* GCDNetworking (Tests) */,\n\t\t\t);\n\t\t};\n/* End PBXProject section */\n\n/* Begin PBXResourcesBuildPhase section */\n\t\tE2B3CEEE19E917BB003ED065 /* Resources */ = {\n\t\t\tisa = PBXResourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXResourcesBuildPhase section */\n\n/* Begin PBXSourcesBuildPhase section */\n\t\tE26DC16319E8494700C68DDC /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2812BB919F2E9780046DDC1 /* GCDTCPClient.m in Sources */,\n\t\t\t\tE2812BC119F2E9780046DDC1 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE26ABC2C19EC9F9A00654D9F /* main.m in Sources */,\n\t\t\t\tE2812BC519F2E9780046DDC1 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2812BBD19F2E9780046DDC1 /* GCDTCPConnection.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE298C46819ED859F00C76821 /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2812BBC19F2E9780046DDC1 /* GCDTCPClient.m in Sources */,\n\t\t\t\tE2812BC419F2E9780046DDC1 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE298C47A19ED866100C76821 /* GCDNetworking_Tests.m in Sources */,\n\t\t\t\tE2812BC819F2E9780046DDC1 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2812BC019F2E9780046DDC1 /* GCDTCPConnection.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE2B3CEEC19E917BB003ED065 /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2812BBA19F2E9780046DDC1 /* GCDTCPClient.m in Sources */,\n\t\t\t\tE2812BC219F2E9780046DDC1 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE2B3CF1D19E91825003ED065 /* main.m in Sources */,\n\t\t\t\tE2B3CF1B19E91825003ED065 /* AppDelegate.m in Sources */,\n\t\t\t\tE2812BC619F2E9780046DDC1 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2812BBE19F2E9780046DDC1 /* GCDTCPConnection.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXSourcesBuildPhase section */\n\n/* Begin PBXTargetDependency section */\n\t\tE2168F9619EE04B200865350 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E298C46B19ED859F00C76821 /* GCDNetworking (Tests) */;\n\t\t\ttargetProxy = E2168F9519EE04B200865350 /* PBXContainerItemProxy */;\n\t\t};\n\t\tE2B3CEEB19E91784003ED065 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E26DC16619E8494700C68DDC /* GCDNetworking (CLT) */;\n\t\t\ttargetProxy = E2B3CEEA19E91784003ED065 /* PBXContainerItemProxy */;\n\t\t};\n\t\tE2B3CF2B19E9189C003ED065 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E2B3CEEF19E917BB003ED065 /* GCDNetworking (iOS) */;\n\t\t\ttargetProxy = E2B3CF2A19E9189C003ED065 /* PBXContainerItemProxy */;\n\t\t};\n/* End PBXTargetDependency section */\n\n/* Begin XCBuildConfiguration section */\n\t\tE26DC16C19E8494700C68DDC /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tALWAYS_SEARCH_USER_PATHS = NO;\n\t\t\t\tCLANG_ENABLE_OBJC_ARC = YES;\n\t\t\t\tENABLE_STRICT_OBJC_MSGSEND = YES;\n\t\t\t\tGCC_C_LANGUAGE_STANDARD = gnu99;\n\t\t\t\tGCC_OPTIMIZATION_LEVEL = 0;\n\t\t\t\tGCC_PREPROCESSOR_DEFINITIONS = \"DEBUG=1\";\n\t\t\t\tONLY_ACTIVE_ARCH = YES;\n\t\t\t\tWARNING_CFLAGS = (\n\t\t\t\t\t\"-Wall\",\n\t\t\t\t\t\"-Weverything\",\n\t\t\t\t\t\"-Wshadow\",\n\t\t\t\t\t\"-Wshorten-64-to-32\",\n\t\t\t\t\t\"-Wno-direct-ivar-access\",\n\t\t\t\t\t\"-Wno-objc-missing-property-synthesis\",\n\t\t\t\t\t\"-Wno-implicit-retain-self\",\n\t\t\t\t\t\"-Wno-documentation-unknown-command\",\n\t\t\t\t\t\"-Wno-gnu-statement-expression\",\n\t\t\t\t\t\"-Wno-reserved-id-macro\",\n\t\t\t\t\t\"-Wno-cstring-format-directive\",\n\t\t\t\t\t\"-Wno-partial-availability\",\n\t\t\t\t);\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE26DC16D19E8494700C68DDC /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tALWAYS_SEARCH_USER_PATHS = NO;\n\t\t\t\tCLANG_ENABLE_OBJC_ARC = YES;\n\t\t\t\tDEBUG_INFORMATION_FORMAT = \"dwarf-with-dsym\";\n\t\t\t\tENABLE_STRICT_OBJC_MSGSEND = YES;\n\t\t\t\tGCC_C_LANGUAGE_STANDARD = gnu99;\n\t\t\t\tGCC_TREAT_WARNINGS_AS_ERRORS = YES;\n\t\t\t\tWARNING_CFLAGS = \"-Wall\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE26DC16F19E8494700C68DDC /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = GCDNetworking;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE26DC17019E8494700C68DDC /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = GCDNetworking;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE298C47419ED859F00C76821 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tFRAMEWORK_SEARCH_PATHS = (\n\t\t\t\t\t\"$(DEVELOPER_FRAMEWORKS_DIR)\",\n\t\t\t\t\t\"$(inherited)\",\n\t\t\t\t);\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = Tests;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE298C47519ED859F00C76821 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tFRAMEWORK_SEARCH_PATHS = (\n\t\t\t\t\t\"$(DEVELOPER_FRAMEWORKS_DIR)\",\n\t\t\t\t\t\"$(inherited)\",\n\t\t\t\t);\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = Tests;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE2B3CEE819E91770003ED065 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tPRODUCT_NAME = \"$(TARGET_NAME)\";\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE2B3CEE919E91770003ED065 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tPRODUCT_NAME = \"$(TARGET_NAME)\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE2B3CF1119E917BC003ED065 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tCODE_SIGN_IDENTITY = \"iPhone Developer\";\n\t\t\t\tDEVELOPMENT_TEAM = 88W3E55T4B;\n\t\t\t\tINFOPLIST_FILE = iOS/Info.plist;\n\t\t\t\tIPHONEOS_DEPLOYMENT_TARGET = 8.0;\n\t\t\t\tPRODUCT_NAME = GCDNetworking;\n\t\t\t\tSDKROOT = iphoneos;\n\t\t\t\tTARGETED_DEVICE_FAMILY = \"1,2\";\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE2B3CF1219E917BC003ED065 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tCODE_SIGN_IDENTITY = \"iPhone Developer\";\n\t\t\t\tDEVELOPMENT_TEAM = 88W3E55T4B;\n\t\t\t\tINFOPLIST_FILE = iOS/Info.plist;\n\t\t\t\tIPHONEOS_DEPLOYMENT_TARGET = 8.0;\n\t\t\t\tPRODUCT_NAME = GCDNetworking;\n\t\t\t\tSDKROOT = iphoneos;\n\t\t\t\tTARGETED_DEVICE_FAMILY = \"1,2\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n/* End XCBuildConfiguration section */\n\n/* Begin XCConfigurationList section */\n\t\tE26DC16219E8494700C68DDC /* Build configuration list for PBXProject \"GCDNetworking\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE26DC16C19E8494700C68DDC /* Debug */,\n\t\t\t\tE26DC16D19E8494700C68DDC /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE26DC16E19E8494700C68DDC /* Build configuration list for PBXNativeTarget \"GCDNetworking (CLT)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE26DC16F19E8494700C68DDC /* Debug */,\n\t\t\t\tE26DC17019E8494700C68DDC /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE298C47619ED859F00C76821 /* Build configuration list for PBXNativeTarget \"GCDNetworking (Tests)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE298C47419ED859F00C76821 /* Debug */,\n\t\t\t\tE298C47519ED859F00C76821 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE2B3CEE719E91770003ED065 /* Build configuration list for PBXAggregateTarget \"Build All\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE2B3CEE819E91770003ED065 /* Debug */,\n\t\t\t\tE2B3CEE919E91770003ED065 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE2B3CF1019E917BC003ED065 /* Build configuration list for PBXNativeTarget \"GCDNetworking (iOS)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE2B3CF1119E917BC003ED065 /* Debug */,\n\t\t\t\tE2B3CF1219E917BC003ED065 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n/* End XCConfigurationList section */\n\t};\n\trootObject = E26DC15F19E8494700C68DDC /* Project object */;\n}\n"
  },
  {
    "path": "GCDNetworking/GCDNetworking.xcodeproj/xcshareddata/xcschemes/Tests.xcscheme",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Scheme\n   LastUpgradeVersion = \"0830\"\n   version = \"1.3\">\n   <BuildAction\n      parallelizeBuildables = \"YES\"\n      buildImplicitDependencies = \"YES\">\n      <BuildActionEntries>\n         <BuildActionEntry\n            buildForTesting = \"YES\"\n            buildForRunning = \"NO\"\n            buildForProfiling = \"NO\"\n            buildForArchiving = \"NO\"\n            buildForAnalyzing = \"NO\">\n            <BuildableReference\n               BuildableIdentifier = \"primary\"\n               BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n               BuildableName = \"Tests.xctest\"\n               BlueprintName = \"GCDNetworking (Tests)\"\n               ReferencedContainer = \"container:GCDNetworking.xcodeproj\">\n            </BuildableReference>\n         </BuildActionEntry>\n      </BuildActionEntries>\n   </BuildAction>\n   <TestAction\n      buildConfiguration = \"Debug\"\n      selectedDebuggerIdentifier = \"Xcode.DebuggerFoundation.Debugger.LLDB\"\n      selectedLauncherIdentifier = \"Xcode.DebuggerFoundation.Launcher.LLDB\"\n      shouldUseLaunchSchemeArgsEnv = \"NO\"\n      enableAddressSanitizer = \"YES\">\n      <Testables>\n         <TestableReference\n            skipped = \"NO\">\n            <BuildableReference\n               BuildableIdentifier = \"primary\"\n               BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n               BuildableName = \"Tests.xctest\"\n               BlueprintName = \"GCDNetworking (Tests)\"\n               ReferencedContainer = \"container:GCDNetworking.xcodeproj\">\n            </BuildableReference>\n         </TestableReference>\n      </Testables>\n      <MacroExpansion>\n         <BuildableReference\n            BuildableIdentifier = \"primary\"\n            BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n            BuildableName = \"Tests.xctest\"\n            BlueprintName = \"GCDNetworking (Tests)\"\n            ReferencedContainer = \"container:GCDNetworking.xcodeproj\">\n         </BuildableReference>\n      </MacroExpansion>\n      <EnvironmentVariables>\n         <EnvironmentVariable\n            key = \"DYLD_INSERT_LIBRARIES\"\n            value = \"/usr/lib/libgmalloc.dylib\"\n            isEnabled = \"YES\">\n         </EnvironmentVariable>\n         <EnvironmentVariable\n            key = \"NSZombieEnabled\"\n            value = \"YES\"\n            isEnabled = \"YES\">\n         </EnvironmentVariable>\n      </EnvironmentVariables>\n      <AdditionalOptions>\n         <AdditionalOption\n            key = \"NSZombieEnabled\"\n            value = \"YES\"\n            isEnabled = \"YES\">\n         </AdditionalOption>\n      </AdditionalOptions>\n   </TestAction>\n   <LaunchAction\n      buildConfiguration = \"Debug\"\n      selectedDebuggerIdentifier = \"Xcode.DebuggerFoundation.Debugger.LLDB\"\n      selectedLauncherIdentifier = \"Xcode.DebuggerFoundation.Launcher.LLDB\"\n      launchStyle = \"0\"\n      useCustomWorkingDirectory = \"NO\"\n      ignoresPersistentStateOnLaunch = \"NO\"\n      debugDocumentVersioning = \"YES\"\n      debugServiceExtension = \"internal\"\n      allowLocationSimulation = \"YES\">\n      <AdditionalOptions>\n      </AdditionalOptions>\n   </LaunchAction>\n   <ProfileAction\n      buildConfiguration = \"Release\"\n      shouldUseLaunchSchemeArgsEnv = \"YES\"\n      savedToolIdentifier = \"\"\n      useCustomWorkingDirectory = \"NO\"\n      debugDocumentVersioning = \"YES\">\n   </ProfileAction>\n   <AnalyzeAction\n      buildConfiguration = \"Release\">\n   </AnalyzeAction>\n   <ArchiveAction\n      buildConfiguration = \"Release\"\n      revealArchiveInOrganizer = \"YES\">\n   </ArchiveAction>\n</Scheme>\n"
  },
  {
    "path": "GCDNetworking/LICENSE",
    "content": "Copyright (c) 2014, Pierre-Olivier Latour\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n    * Redistributions of source code must retain the above copyright\n      notice, this list of conditions and the following disclaimer.\n    * Redistributions in binary form must reproduce the above copyright\n      notice, this list of conditions and the following disclaimer in the\n      documentation and/or other materials provided with the distribution.\n    * The name of Pierre-Olivier Latour may not be used to endorse\n      or promote products derived from this software without specific\n      prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\nDIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\nON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "GCDNetworking/README.md",
    "content": "Overview\n========\n\n[![Build Status](https://travis-ci.org/swisspol/GCDNetworking.svg?branch=master)](https://travis-ci.org/swisspol/GCDNetworking)\n\nGCDNetworking is a networking framework based on GCD available under a friendly [New BSD License](LICENSE).\n\nRequirements:\n* OS X 10.8 or later (x86_64)\n* iOS 5.8 or later (armv7, armv7s or arm64)\n* ARC memory management only\n"
  },
  {
    "path": "GCDNetworking/Run-Tests.sh",
    "content": "#!/bin/bash -ex\n\nOSX_SDK=\"macosx\"\nif [ -z \"$TRAVIS\" ]; then\n  IOS_SDK=\"iphoneos\"\nelse\n  IOS_SDK=\"iphonesimulator\"\nfi\n\nOSX_TARGET=\"GCDNetworking (CLT)\"\nIOS_TARGET=\"GCDNetworking (iOS)\"\nCONFIGURATION=\"Release\"\n\nBUILD_DIR=\"/tmp/GCDNetworking\"\nPRODUCT=\"$BUILD_DIR/$CONFIGURATION/GCDNetworking\"\n\n# Build for iOS for oldest deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$IOS_SDK\" -target \"$IOS_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\" \"IPHONEOS_DEPLOYMENT_TARGET=8.0\"\n\n# Build for iOS for default deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$IOS_SDK\" -target \"$IOS_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\"\n\n# Build for OS X for oldest deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$OSX_SDK\" -target \"$OSX_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\" \"MACOSX_DEPLOYMENT_TARGET=10.8\"\n\n# Build for OS X for default deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$OSX_SDK\" -target \"$OSX_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\"\n\n# Run tests\nxcodebuild test -scheme \"Tests\"\n\n# Done\necho \"\\nAll tests completed successfully!\"\n"
  },
  {
    "path": "GCDNetworking/Tests/GCDNetworking_Tests.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#pragma clang diagnostic ignored \"-Wgnu-zero-variadic-macro-arguments\"\n#pragma clang diagnostic ignored \"-Wsign-compare\"\n\n#import <XCTest/XCTest.h>\n\n#import \"GCDNetworking.h\"\n\n#define kTestPort 3333\n\ntypedef void (^TCPServerConnectionBlock)(GCDTCPPeerConnection* connection);\n\n@interface TCPServer : GCDTCPServer\n@end\n\n@implementation TCPServer {\n@private\n  TCPServerConnectionBlock _block;\n}\n\n- (id)initWithPort:(NSUInteger)port connectionBlock:(TCPServerConnectionBlock)block {\n  if ((self = [super initWithConnectionClass:[GCDTCPServerConnection class] port:port])) {\n    _block = block;\n  }\n  return self;\n}\n\n- (void)willOpenConnection:(GCDTCPPeerConnection*)connection {\n  [super willOpenConnection:connection];\n\n  _block(connection);\n}\n\n@end\n\n@interface GCDNetworking_Tests : XCTestCase\n@end\n\n@implementation GCDNetworking_Tests\n\n- (void)testReading {\n  __block GCDTCPPeerConnection* inConnection = nil;\n  TCPServer* server = [[TCPServer alloc] initWithPort:kTestPort\n                                      connectionBlock:^(GCDTCPPeerConnection* connection) {\n                                        inConnection = connection;\n                                      }];\n  XCTAssertTrue([server start]);\n\n  GCDTCPClient* client = [[GCDTCPClient alloc] initWithConnectionClass:[GCDTCPClientConnection class] host:@\"localhost\" port:kTestPort];\n  XCTAssertTrue([client start]);\n\n  sleep(1);\n\n  XCTAssertNotNil(inConnection);\n  GCDTCPClientConnection* outConnection = client.connection;\n  XCTAssertNotNil(outConnection);\n\n  NSData* data1 = [inConnection readDataWithTimeout:3.0];\n  XCTAssertNil(data1);\n\n  XCTestExpectation* expectation = [self expectationWithDescription:@\"\"];\n  [outConnection writeDataAsynchronously:[@\"Hello World!\\n\" dataUsingEncoding:NSUTF8StringEncoding]\n                              completion:^(BOOL success) {\n                                XCTAssertTrue(success);\n                                [expectation fulfill];\n                              }];\n  [self waitForExpectationsWithTimeout:10.0 handler:NULL];\n  NSData* data2 = [inConnection readDataWithTimeout:3.0];\n  XCTAssertNotNil(data2);\n  NSString* string = [[NSString alloc] initWithData:data2 encoding:NSUTF8StringEncoding];\n  XCTAssertEqualObjects(string, @\"Hello World!\\n\");\n\n  [outConnection close];\n  [inConnection close];\n\n  [client stop];\n  [server stop];\n}\n\n- (void)testWriting {\n  __block GCDTCPPeerConnection* inConnection = nil;\n  TCPServer* server = [[TCPServer alloc] initWithPort:kTestPort\n                                      connectionBlock:^(GCDTCPPeerConnection* connection) {\n                                        inConnection = connection;\n                                      }];\n  XCTAssertTrue([server start]);\n\n  GCDTCPClient* client = [[GCDTCPClient alloc] initWithConnectionClass:[GCDTCPClientConnection class] host:@\"localhost\" port:kTestPort];\n  XCTAssertTrue([client start]);\n\n  sleep(1);\n\n  XCTAssertNotNil(inConnection);\n  GCDTCPClientConnection* outConnection = client.connection;\n  XCTAssertNotNil(outConnection);\n\n  XCTestExpectation* expectation = [self expectationWithDescription:@\"\"];\n  [inConnection readDataAsynchronously:^(NSData* data) {\n    XCTAssertNotNil(data);\n    NSString* string = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];\n    XCTAssertEqualObjects(string, @\"Hello World!\\n\");\n\n    [expectation fulfill];\n  }];\n  BOOL success = [outConnection writeData:[@\"Hello World!\\n\" dataUsingEncoding:NSUTF8StringEncoding] withTimeout:3.0];\n  XCTAssertTrue(success);\n  [self waitForExpectationsWithTimeout:10.0 handler:NULL];\n\n  [outConnection close];\n  [inConnection close];\n\n  [client stop];\n  [server stop];\n}\n\n@end\n"
  },
  {
    "path": "GCDNetworking/iOS/AppDelegate.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <UIKit/UIKit.h>\n\n@interface AppDelegate : UIResponder <UIApplicationDelegate>\n@property(retain, nonatomic) UIWindow* window;\n@end\n"
  },
  {
    "path": "GCDNetworking/iOS/AppDelegate.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"AppDelegate.h\"\n#import \"GCDNetworking.h\"\n\n@interface Connection : GCDTCPServerConnection\n@end\n\n@implementation Connection\n\n- (void)didOpen {\n  [super didOpen];\n\n  NSString* welcome = @\"Hello World!\\n\";\n  [self writeDataAsynchronously:[welcome dataUsingEncoding:NSUTF8StringEncoding]\n                     completion:^(BOOL success) {\n                       [self close];\n                     }];\n}\n\n@end\n\n@implementation AppDelegate\n\n- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {\n  _window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];\n  _window.backgroundColor = [UIColor whiteColor];\n  _window.rootViewController = [[UIViewController alloc] init];\n  _window.rootViewController.view = [[UIView alloc] init];\n  [_window makeKeyAndVisible];\n\n  GCDTCPServer* server = [[GCDTCPServer alloc] initWithConnectionClass:[Connection class] port:2323];\n  if (![server start]) {\n    abort();\n  }\n  NSLog(@\"TCP server running on %@\", GCDTCPServerGetPrimaryIPAddress(false));\n\n  return YES;\n}\n@end\n"
  },
  {
    "path": "GCDNetworking/iOS/Info.plist",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">\n<plist version=\"1.0\">\n<dict>\n\t<key>CFBundleDevelopmentRegion</key>\n\t<string>en</string>\n\t<key>CFBundleDisplayName</key>\n\t<string>${PRODUCT_NAME}</string>\n\t<key>CFBundleExecutable</key>\n\t<string>${EXECUTABLE_NAME}</string>\n\t<key>CFBundleIdentifier</key>\n\t<string>net.pol-online.${PRODUCT_NAME:rfc1034identifier}</string>\n\t<key>CFBundleInfoDictionaryVersion</key>\n\t<string>6.0</string>\n\t<key>CFBundleName</key>\n\t<string>${PRODUCT_NAME}</string>\n\t<key>CFBundlePackageType</key>\n\t<string>APPL</string>\n\t<key>CFBundleShortVersionString</key>\n\t<string>1.0</string>\n\t<key>CFBundleVersion</key>\n\t<string>1.0</string>\n\t<key>LSRequiresIPhoneOS</key>\n\t<true/>\n\t<key>UIRequiredDeviceCapabilities</key>\n\t<array>\n\t\t<string>armv7</string>\n\t</array>\n\t<key>UISupportedInterfaceOrientations</key>\n\t<array>\n\t\t<string>UIInterfaceOrientationPortrait</string>\n\t\t<string>UIInterfaceOrientationLandscapeLeft</string>\n\t\t<string>UIInterfaceOrientationLandscapeRight</string>\n\t</array>\n\t<key>UISupportedInterfaceOrientations~ipad</key>\n\t<array>\n\t\t<string>UIInterfaceOrientationPortrait</string>\n\t\t<string>UIInterfaceOrientationPortraitUpsideDown</string>\n\t\t<string>UIInterfaceOrientationLandscapeLeft</string>\n\t\t<string>UIInterfaceOrientationLandscapeRight</string>\n\t</array>\n</dict>\n</plist>\n"
  },
  {
    "path": "GCDNetworking/iOS/main.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"AppDelegate.h\"\n\nint main(int argc, char* argv[]) {\n  @autoreleasepool {\n    return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));\n  }\n}\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetConnection.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDNetworking.h\"\n\n/**\n *  The GCDTelnetConnection class is the class used to implement connections\n *  for GCDTelnetServer.\n */\n@interface GCDTelnetConnection : GCDTCPServerConnection\n\n/*\n *  Returns the type of the remote terminal.\n *\n *  @warning This will only be non-nil if the connected peer responded to the\n *  corresponding Telnet command.\n */\n@property(nonatomic, readonly) NSString* terminalType;\n\n/*\n *  Returns YES if the remote terminal is a color one.\n */\n@property(nonatomic, readonly, getter=isColorTerminal) BOOL colorTerminal;\n\n/*\n *  Sets the prompt to show at the beginning of a new line.\n *\n *  Set this value to nil to remove the prompt entirely.\n *\n *  The default value is \"> \".\n *\n *  @warning Setting this value to a non-ASCII string or changing it outside\n *  of the scope of the GCDTelnetServer start handler is not supported.\n */\n@property(nonatomic, copy) NSString* prompt;\n\n/*\n *  Sets the placeholder string inserted when the tab key is pressed.\n *\n *  The default value is \"\\t\".\n *\n *  @warning Setting this value to a non-ASCII string or changing it outside\n *  of the scope of the GCDTelnetServer start handler is not supported.\n */\n@property(nonatomic, copy) NSString* tabPlaceholder;\n\n/*\n *  Sets the maximum number of lines preserved by the history.\n *\n *  Set this value to 0 to disable the history entirely.\n *\n *  The default value is NSIntegerMax i.e. unlimited.\n *\n *  @warning Changing this value outside of the scope of the GCDTelnetServer\n *  start handler is not supported.\n */\n@property(nonatomic) NSUInteger maxHistorySize;\n\n@end\n\n@interface GCDTelnetConnection (Subclassing)\n\n/*\n *  Direct access to the line buffer used by the connection.\n *\n *  @warning This string must only contain ASCII characters.\n */\n@property(nonatomic, readonly) NSMutableString* lineBuffer;\n\n/*\n *  Called whenever a new connection has started with a remote terminal.\n *\n *  The default implementation calls the GCDTelnetServer start handler.\n */\n- (NSString*)start;\n\n/*\n *  Called when the arrow up key is pressed.\n *\n *  The default implementation navigates the history towards older entries.\n */\n- (NSData*)processCursorUp;\n\n/*\n *  Called when the arrow up key is pressed.\n *\n *  The default implementation navigates the history towards newer entries.\n */\n- (NSData*)processCursorDown;\n\n/*\n *  Called when the arrow right key is pressed.\n *\n *  The default implementation just beeps.\n */\n- (NSData*)processCursorForward;\n\n/*\n *  Called when the arrow left key is pressed.\n *\n *  The default implementation just beeps.\n */\n- (NSData*)processCursorBack;\n\n/*\n *  Called when an unimplemented ANSI escape sequence has been received.\n *\n *  The default implementation just beeps.\n */\n- (NSData*)processOtherANSIEscapeSequence:(NSData*)data;\n\n/*\n *  Called when the tab key is pressed.\n *\n *  The default implementation inserts the tab placeholder string.\n */\n- (NSData*)processTab;\n\n/*\n *  Called when the delete key is pressed.\n *\n *  The default implementation deletes the last character.\n */\n- (NSData*)processDelete;\n\n/*\n *  Called when the return key is pressed.\n *\n *  The default implementation calls -processLine: and updates the history.\n */\n- (NSData*)processCarriageReturn;\n\n/*\n *  Called when any other ASCII character has been received.\n *\n *  The default implementation inserts the character.\n */\n- (NSData*)processOtherASCIICharacter:(unsigned char)character;\n\n/*\n *  Called when a non-ASCII character has been received.\n *\n *  The default implementation does nothing.\n */\n- (NSData*)processNonASCIICharacter:(unsigned char)character;\n\n/*\n *  Called whenever input data has been received from the remote terminal.\n *\n *  The default implementation parses the data and calls one of the other\n *  methods.\n */\n- (NSData*)processRawInput:(NSData*)input;\n\n/*\n *  Called whenever a line has been fully received from the remote terminal.\n *\n *  The default implementation calls the GCDTelnetServer line handler.\n */\n- (NSString*)processLine:(NSString*)line;\n\n@end\n\n@interface GCDTelnetConnection (Extensions)\n\n/**\n *  Parses a line like a command line interface extracting the command and\n *  arguments.\n *\n *  This methods supports quoted arguments using single or double quotes.\n */\n- (NSArray*)parseLineAsCommandAndArguments:(NSString*)line;\n\n/**\n *  Returns a sanitized version of a string suitable for sending to the remote\n *  terminal.\n *\n *  The current implementation replaces all newline characters by carriage\n *  returns.\n */\n- (NSString*)sanitizeStringForTerminal:(NSString*)string;\n\n/*\n *  Convenience methods that writes a string to the connection using lossy\n *  ASCII encoding.\n */\n- (BOOL)writeASCIIString:(NSString*)string withTimeout:(NSTimeInterval)timeout;\n\n/*\n *  Convenience methods that writes a formatted string to the connection using\n *  lossy ASCII encoding.\n */\n- (void)writeASCIIStringAsynchronously:(NSString*)string completion:(void (^)(BOOL success))completion;\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetConnection.m",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTelnetPrivate.h\"\n\n#define kTelnetCommandStringsOffset kTelnetCommand_SE\n\n#define kCSIPrefix \"\\x1b[\"  // https://en.wikipedia.org/wiki/ANSI_escape_code\n#define kCarriageReturnString @\"\\r\\n\"\n\n#define kSynchronousCommunicationTimeout 3.0\n\nstatic const char* _telnetCommandStrings[] = {\n    \"SE\", \"NOP\", \"DM\", \"BRK\", \"IP\", \"AO\", \"AYT\", \"EC\", \"EL\", \"GA\", \"SB\", \"WILL\", \"WONT\", \"DO\", \"DONT\", \"IAC\"};\n\nstatic const char* _telnetOptionStrings[] = {\n    NULL, \"Echo\", NULL, \"Supress Go Ahead\", NULL, \"Status\", \"Timing Mark\", NULL, NULL, NULL,  // 0-9\n    NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,  // 10-29\n    NULL, NULL, NULL, NULL, \"Terminal Type\", NULL, NULL, NULL, NULL, NULL,  // 20-29\n    NULL, \"Window Size\", \"Terminal Speed\", \"Remote Flow Control\", \"Linemode\", NULL, \"Environment Variables\", NULL, NULL, NULL  // 30-39\n};\n\nstatic NSRegularExpression* _commandLineParser = nil;\n\n@interface GCDTelnetConnection () {\n@private\n  NSMutableString* _lineBuffer;\n  NSMutableArray* _historyLines;\n  NSUInteger _historyIndex;\n  NSString* _savedLine;\n}\n@end\n\n@implementation GCDTelnetConnection\n\n+ (void)initialize {\n  if (self == [GCDTelnetConnection class]) {\n    _commandLineParser = [[NSRegularExpression alloc] initWithPattern:@\"(\\\"[^\\\"]+\\\"|'[^']+'|[^\\\\s\\\"]+)\" options:0 error:NULL];\n    _LOG_DEBUG_CHECK(_commandLineParser);\n  }\n}\n\n- (instancetype)initWithSocket:(int)socket {\n  if ((self = [super initWithSocket:socket])) {\n    _lineBuffer = [[NSMutableString alloc] init];\n    _prompt = @\"> \";\n    _tabPlaceholder = @\"\\t\";\n    _maxHistorySize = NSIntegerMax;\n    _historyLines = [[NSMutableArray alloc] init];\n    _historyIndex = NSNotFound;\n  }\n  return self;\n}\n\nstatic NSString* _StringFromIACBuffer(const unsigned char* buffer, NSUInteger length) {\n  _LOG_DEBUG_CHECK(buffer[0] == kTelnetCommand_IAC);\n  _LOG_DEBUG_CHECK(length >= 3);\n  NSMutableString* string = [[NSMutableString alloc] init];\n  NSUInteger i = 0;\n  while (i < length) {\n    [string appendFormat:@\"%s, %s\", _telnetCommandStrings[buffer[i] - kTelnetCommandStringsOffset], _telnetCommandStrings[buffer[i + 1] - kTelnetCommandStringsOffset]];\n    i += 2;\n    if ((buffer[i - 1] >= kTelnetCommand_WILL) && (buffer[i - 1] <= kTelnetCommand_DONT)) {\n      [string appendFormat:@\", %s\", _telnetOptionStrings[buffer[i]]];\n      ++i;\n    } else if (buffer[i - 1] == kTelnetCommand_SB) {\n      [string appendFormat:@\", %s,\", _telnetOptionStrings[buffer[i]]];\n      ++i;\n      while ((buffer[i] != kTelnetCommand_IAC) || (buffer[i + 1] != kTelnetCommand_SE)) {\n        [string appendFormat:@\" (%i)'%c'\", buffer[i], buffer[i]];\n        ++i;\n      }\n      [string appendFormat:@\", %s, %s\", _telnetCommandStrings[buffer[i] - kTelnetCommandStringsOffset], _telnetCommandStrings[buffer[i + 1] - kTelnetCommandStringsOffset]];\n      i += 2;\n    } else {\n      [string appendFormat:@\", %i\", buffer[i]];\n      ++i;\n    }\n  }\n  return string;\n}\n\n- (NSData*)_sendIACBuffer:(const unsigned char*)buffer length:(NSUInteger)length {\n  _LOG_DEBUG_CHECK(buffer[0] == kTelnetCommand_IAC);\n\n  if (![self writeBuffer:buffer length:length withTimeout:kSynchronousCommunicationTimeout]) {\n    _LOG_ERROR(@\"Failed sending Telnet command: %@\", _StringFromIACBuffer(buffer, length));\n    return nil;\n  }\n  _LOG_DEBUG(@\"Telnet IAC (->) %@\", _StringFromIACBuffer(buffer, length));\n\n  NSData* data = [self readDataWithTimeout:kSynchronousCommunicationTimeout];\n  if (!data.length) {\n    return nil;\n  }\n  const unsigned char* bytes = data.bytes;\n  if (bytes[0] != kTelnetCommand_IAC) {\n    _LOG_ERROR(@\"Invalid Telnet command received\");\n    return nil;\n  }\n  _LOG_DEBUG(@\"Telnet IAC (<-) %@\", _StringFromIACBuffer(data.bytes, data.length));\n\n  return data;\n}\n\n- (BOOL)_setIACOption:(unsigned char)option {\n  unsigned char buffer[] = {kTelnetCommand_IAC, kTelnetCommand_WILL, option};\n  NSData* data = [self _sendIACBuffer:buffer length:sizeof(buffer)];\n  if (data.length != 3) {\n    return NO;\n  }\n  const unsigned char* bytes = data.bytes;\n  if ((bytes[1] != kTelnetCommand_DO) || (bytes[2] != option)) {\n    _LOG_ERROR(@\"Failed setting Telnet option: %@\", _StringFromIACBuffer(data.bytes, data.length));\n    return NO;\n  }\n  return YES;\n}\n\n- (NSString*)_retrieveTerminalType {\n  unsigned char buffer1[] = {kTelnetCommand_IAC, kTelnetCommand_DO, kTelnetOption_TerminalType};\n  NSData* data1 = [self _sendIACBuffer:buffer1 length:sizeof(buffer1)];\n  if (data1.length != 3) {\n    return nil;\n  }\n  const unsigned char* bytes1 = data1.bytes;\n  if ((bytes1[1] != kTelnetCommand_WILL) || (bytes1[2] != kTelnetOption_TerminalType)) {\n    return nil;\n  }\n\n  unsigned char buffer2[] = {kTelnetCommand_IAC, kTelnetCommand_SB, kTelnetOption_TerminalType, 1, kTelnetCommand_IAC, kTelnetCommand_SE};\n  NSData* data2 = [self _sendIACBuffer:buffer2 length:sizeof(buffer2)];\n  if (data2.length < 6) {\n    return nil;\n  }\n  const unsigned char* bytes2 = data2.bytes;\n  NSUInteger length2 = data2.length;\n  if ((bytes2[1] != kTelnetCommand_SB) || (bytes2[2] != kTelnetOption_TerminalType) || (bytes2[3] != 0)) {\n    return nil;\n  }\n  if ((bytes2[length2 - 2] != kTelnetCommand_IAC) || (bytes2[length2 - 1] != kTelnetCommand_SE)) {\n    return nil;\n  }\n\n  return [[NSString alloc] initWithBytes:&bytes2[4] length:(length2 - 6) encoding:NSASCIIStringEncoding];\n}\n\n- (void)_readInput {\n  [self readDataAsynchronously:^(NSData* data) {\n    if (data.length) {\n      data = [self processRawInput:data];\n      if (data) {\n        [self writeDataAsynchronously:data\n                           completion:^(BOOL success) {\n                             if (success) {\n                               [self _readInput];\n                             } else {\n                               [self close];\n                             }\n                           }];\n      } else {\n        [self _readInput];\n      }\n    } else {\n      [self close];\n    }\n  }];\n}\n\n- (void)didOpen {\n  [self _setIACOption:kTelnetOption_SuppressGoAhead];\n  [self _setIACOption:kTelnetOption_Echo];\n\n  _terminalType = [self _retrieveTerminalType];\n  if (_terminalType.length) {\n    NSRange range = [_terminalType rangeOfString:@\"color\" options:NSCaseInsensitiveSearch];\n    _colorTerminal = (range.location != NSNotFound);\n  } else {\n    _LOG_ERROR(@\"Failed retrieving Telnet terminal type from %@\", self.remoteIPAddress);\n  }\n  NSMutableString* string = [[NSMutableString alloc] init];\n  NSString* start = [self start];\n  if (start) {\n    [string appendString:start];\n  }\n  if (_prompt) {\n    [string appendString:_prompt];\n  }\n  if (string.length) {\n    [self writeASCIIStringAsynchronously:string\n                              completion:^(BOOL success) {\n                                if (success) {\n                                  [self _readInput];\n                                } else {\n                                  [self close];\n                                }\n                              }];\n  } else {\n    [self _readInput];\n  }\n}\n\n@end\n\n@implementation GCDTelnetConnection (Subclassing)\n\n- (NSMutableString*)lineBuffer {\n  return _lineBuffer;\n}\n\n- (NSString*)start {\n  GCDTelnetStartHandler handler = [(GCDTelnetServer*)self.peer startHandler];\n  if (handler) {\n    return [self sanitizeStringForTerminal:handler(self)];\n  }\n  return nil;\n}\n\n- (NSData*)_beepData {\n  unsigned char buffer[] = {kControlCode_BEL};\n  return [NSData dataWithBytes:buffer length:sizeof(buffer)];\n}\n\n- (NSMutableData*)_emptyLineData {\n  unsigned char buffer[] = {\n      kCSIPrefix[0], kCSIPrefix[1], '2', 'K',  // Clear entire line\n      kCSIPrefix[0], kCSIPrefix[1], '1', 'G'  // Move cursor to column 1\n  };\n  NSMutableData* data = [NSMutableData dataWithBytes:buffer length:sizeof(buffer)];\n  if (_prompt) {\n    [data appendData:(id)[_prompt dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES]];\n  }\n  return data;\n}\n\n- (NSData*)_stringLineData:(NSString*)string {\n  [_lineBuffer setString:string];\n  NSMutableData* data = [self _emptyLineData];\n  [data appendData:(id)[string dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES]];\n  return data;\n}\n\n- (NSData*)processCursorUp {\n  if ((_historyIndex == NSNotFound) && _historyLines.count) {\n    _savedLine = [_lineBuffer copy];\n    _historyIndex = _historyLines.count - 1;\n  } else if ((_historyIndex != NSNotFound) && (_historyIndex > 0)) {\n    _historyIndex -= 1;\n  } else {\n    return [self _beepData];\n  }\n  return [self _stringLineData:_historyLines[_historyIndex]];\n}\n\n- (NSData*)processCursorDown {\n  if (_historyIndex == NSNotFound) {\n    return [self _beepData];\n  }\n  NSString* string;\n  if (_historyIndex < _historyLines.count - 1) {\n    _historyIndex += 1;\n    string = _historyLines[_historyIndex];\n  } else {\n    string = _savedLine;\n    _historyIndex = NSNotFound;\n    _savedLine = nil;\n  }\n  return [self _stringLineData:string];\n}\n\n- (NSData*)processCursorForward {\n  return [self _beepData];\n}\n\n- (NSData*)processCursorBack {\n  return [self _beepData];\n}\n\n- (NSData*)processOtherANSIEscapeSequence:(NSData*)data {\n  return [self _beepData];\n}\n\n- (NSData*)processTab {\n  [_lineBuffer appendString:_tabPlaceholder];\n  return [_tabPlaceholder dataUsingEncoding:NSASCIIStringEncoding];\n}\n\n- (NSData*)processDelete {\n  if (_lineBuffer.length) {\n    [_lineBuffer deleteCharactersInRange:NSMakeRange(_lineBuffer.length - 1, 1)];\n    unsigned char buffer[] = {0x08, 0x20, 0x08};  // http://stackoverflow.com/questions/1689554/telnet-server-backspace-delete-not-working\n    return [NSData dataWithBytes:buffer length:sizeof(buffer)];\n  }\n  return [self _beepData];\n}\n\n- (NSData*)processCarriageReturn {\n  NSData* data;\n  NSString* line = [_lineBuffer copy];\n  NSString* result = [self processLine:line];\n  if (result) {\n    if (_maxHistorySize && line.length) {\n      if (!_historyLines.count || ![line isEqualToString:(id)[_historyLines lastObject]]) {\n        [_historyLines addObject:line];\n        if (_historyLines.count > _maxHistorySize) {\n          [_historyLines removeObjectsInRange:NSMakeRange(0, _historyLines.count - _maxHistorySize)];\n        }\n      }\n    }\n    _historyIndex = NSNotFound;\n    _savedLine = nil;\n\n    NSMutableString* string = [[NSMutableString alloc] init];\n    [string appendString:kCarriageReturnString];\n    [string appendString:result];\n    if (_prompt) {\n      [string appendString:_prompt];\n    }\n    data = [string dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES];\n  } else {\n    data = [self _emptyLineData];\n  }\n  [_lineBuffer setString:@\"\"];\n  return data;\n}\n\n- (NSData*)processOtherASCIICharacter:(unsigned char)character {\n  [_lineBuffer appendFormat:@\"%c\", character];\n  return [NSData dataWithBytes:&character length:1];\n}\n\n- (NSData*)processNonASCIICharacter:(unsigned char)character {\n  return nil;\n}\n\n- (NSData*)processRawInput:(NSData*)input {\n  const unsigned char* bytes = input.bytes;\n  NSUInteger length = input.length;\n\n  if ((length > 2) && (bytes[0] == kCSIPrefix[0]) && (bytes[1] == kCSIPrefix[1])) {\n    if (length == 3) {\n      switch (bytes[2]) {\n        case 'A':\n          return [self processCursorUp];\n        case 'B':\n          return [self processCursorDown];\n        case 'C':\n          return [self processCursorForward];\n        case 'D':\n          return [self processCursorBack];\n      }\n    }\n    return [self processOtherANSIEscapeSequence:input];\n  }\n\n  NSMutableData* output = [[NSMutableData alloc] init];\n  while (length) {\n    NSData* data = nil;\n    if ((length >= 2) && (bytes[0] == kControlCode_CR) && (bytes[1] == kControlCode_NUL)) {\n      data = [self processCarriageReturn];\n      bytes += 2;\n      length -= 2;\n    } else {\n      switch (bytes[0]) {\n        case 0x09:\n          data = [self processTab];\n          break;\n\n        case 0x7F:\n          data = [self processDelete];\n          break;\n\n        default:\n          if (bytes[0] <= 127) {\n            data = [self processOtherASCIICharacter:bytes[0]];\n          } else {\n            data = [self processNonASCIICharacter:bytes[0]];\n          }\n          break;\n      }\n      bytes += 1;\n      length -= 1;\n    }\n    if (data.length) {\n      [output appendData:data];\n    }\n  }\n\n  return output;\n}\n\n- (NSString*)processLine:(NSString*)line {\n  GCDTelnetLineHandler handler = [(GCDTelnetServer*)self.peer lineHandler];\n  if (handler) {\n    return [self sanitizeStringForTerminal:handler(self, line)];\n  }\n  return nil;\n}\n\n@end\n\n@implementation GCDTelnetConnection (Extensions)\n\n- (NSArray*)parseLineAsCommandAndArguments:(NSString*)line {\n  NSMutableArray* array = [[NSMutableArray alloc] init];\n  [_commandLineParser enumerateMatchesInString:line\n                                       options:0\n                                         range:NSMakeRange(0, line.length)\n                                    usingBlock:^(NSTextCheckingResult* result, NSMatchingFlags flags, BOOL* stop) {\n                                      NSString* string = [line substringWithRange:result.range];\n                                      if (([string hasPrefix:@\"\\\"\"] && [string hasSuffix:@\"\\\"\"]) || ([string hasPrefix:@\"'\"] && [string hasSuffix:@\"'\"])) {  // TODO: Strip quotes directly in Regex\n                                        [array addObject:[string substringWithRange:NSMakeRange(1, string.length - 2)]];\n                                      } else {\n                                        [array addObject:string];\n                                      }\n                                    }];\n  return array;\n}\n\n- (NSString*)sanitizeStringForTerminal:(NSString*)string {\n  return [string stringByReplacingOccurrencesOfString:@\"\\n\" withString:kCarriageReturnString];\n}\n\n- (BOOL)writeASCIIString:(NSString*)string withTimeout:(NSTimeInterval)timeout {\n  return [self writeData:[string dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES] withTimeout:timeout];\n}\n\n- (void)writeASCIIStringAsynchronously:(NSString*)string completion:(void (^)(BOOL success))completion {\n  [self writeDataAsynchronously:[string dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES] completion:completion];\n}\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetLogging.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <Foundation/Foundation.h>\n\n/**\n *  Automatically detect if XLFacility is available and if so use it as a\n *  logging facility.\n */\n\n#if defined(__has_include) && __has_include(\"XLFacilityMacros.h\")\n\n#define __GCDNETWORKING_LOGGING_FACILITY_XLFACILITY__\n\n#undef XLOG_TAG\n#define XLOG_TAG @\"gcdnetworking.internal\"\n\n#import \"XLFacilityMacros.h\"\n\n#define GN_LOG_DEBUG(...) XLOG_DEBUG(__VA_ARGS__)\n#define GN_LOG_VERBOSE(...) XLOG_VERBOSE(__VA_ARGS__)\n#define GN_LOG_INFO(...) XLOG_INFO(__VA_ARGS__)\n#define GN_LOG_WARNING(...) XLOG_WARNING(__VA_ARGS__)\n#define GN_LOG_ERROR(...) XLOG_ERROR(__VA_ARGS__)\n#define GN_LOG_EXCEPTION(__EXCEPTION__) XLOG_EXCEPTION(__EXCEPTION__)\n\n#define GN_DCHECK(__CONDITION__) XLOG_DEBUG_CHECK(__CONDITION__)\n#define GN_DNOT_REACHED() XLOG_DEBUG_UNREACHABLE()\n\n/**\n *  Automatically detect if CocoaLumberJack is available and if so use\n *  it as a logging facility.\n */\n\n#elif defined(__has_include) && __has_include(\"DDLogMacros.h\")\n\n#import \"DDLogMacros.h\"\n\n#define __GCDNETWORKING_LOGGING_FACILITY_COCOALUMBERJACK__\n\n#undef LOG_LEVEL_DEF\n#define LOG_LEVEL_DEF GCDNetworkingLogLevel\nextern int GCDNetworkingLogLevel;\n\n#define GN_LOG_DEBUG(...) DDLogDebug(__VA_ARGS__)\n#define GN_LOG_VERBOSE(...) DDLogVerbose(__VA_ARGS__)\n#define GN_LOG_INFO(...) DDLogInfo(__VA_ARGS__)\n#define GN_LOG_WARNING(...) DDLogWarn(__VA_ARGS__)\n#define GN_LOG_ERROR(...) DDLogError(__VA_ARGS__)\n#define GN_LOG_EXCEPTION(__EXCEPTION__) DDLogError(@\"%@\", __EXCEPTION__)\n\n/**\n *  Check if a custom logging facility should be used instead.\n */\n\n#elif defined(__GCDNETWORKING_LOGGING_HEADER__)\n\n#define __GCDNETWORKING_LOGGING_FACILITY_CUSTOM__\n\n#import __GCDNETWORKING_LOGGING_HEADER__\n\n/**\n *  If all of the above fail, then use GCDNetworking built-in\n *  logging facility.\n */\n\n#else\n\n#define __GCDNETWORKING_LOGGING_FACILITY_BUILTIN__\n\ntypedef NS_ENUM(int, GCDNetworkingLoggingLevel) {\n  kGCDNetworkingLoggingLevel_Debug = 0,\n  kGCDNetworkingLoggingLevel_Verbose,\n  kGCDNetworkingLoggingLevel_Info,\n  kGCDNetworkingLoggingLevel_Warning,\n  kGCDNetworkingLoggingLevel_Error,\n  kGCDNetworkingLoggingLevel_Exception,\n};\n\nextern GCDNetworkingLoggingLevel GCDNetworkingLogLevel;\nextern void GCDNetworkingLogMessage(GCDNetworkingLoggingLevel level, NSString* format, ...) NS_FORMAT_FUNCTION(2, 3);\n\n#if DEBUG\n#define GN_LOG_DEBUG(...)                                                                                                                  \\\n  do {                                                                                                                                     \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Debug) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Debug, __VA_ARGS__); \\\n  } while (0)\n#else\n#define GN_LOG_DEBUG(...)\n#endif\n#define GN_LOG_VERBOSE(...)                                                                                                                    \\\n  do {                                                                                                                                         \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Verbose) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Verbose, __VA_ARGS__); \\\n  } while (0)\n#define GN_LOG_INFO(...)                                                                                                                 \\\n  do {                                                                                                                                   \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Info) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Info, __VA_ARGS__); \\\n  } while (0)\n#define GN_LOG_WARNING(...)                                                                                                                    \\\n  do {                                                                                                                                         \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Warning) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Warning, __VA_ARGS__); \\\n  } while (0)\n#define GN_LOG_ERROR(...)                                                                                                                  \\\n  do {                                                                                                                                     \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Error) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Error, __VA_ARGS__); \\\n  } while (0)\n#define GN_LOG_EXCEPTION(__EXCEPTION__)                                                                                                                     \\\n  do {                                                                                                                                                      \\\n    if (GCDNetworkingLogLevel <= kGCDNetworkingLoggingLevel_Exception) GCDNetworkingLogMessage(kGCDNetworkingLoggingLevel_Exception, @\"%@\", __EXCEPTION__); \\\n  } while (0)\n\n#endif\n\n/**\n *  Consistency check macros used when building Debug only.\n */\n\n#if !defined(GN_DCHECK) || !defined(GN_DNOT_REACHED)\n\n#if DEBUG\n\n#define GN_DCHECK(__CONDITION__) \\\n  do {                           \\\n    if (!(__CONDITION__)) {      \\\n      abort();                   \\\n    }                            \\\n  } while (0)\n#define GN_DNOT_REACHED() abort()\n\n#else\n\n#define GN_DCHECK(__CONDITION__)\n#define GN_DNOT_REACHED()\n\n#endif\n\n#endif\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetLoggingBridgePrivate.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <Foundation/Foundation.h>\n\n/**\n *  Automatically detect if XLFacility is available.\n */\n\n#if defined(__has_include) && __has_include(\"XLFacilityMacros.h\")\n\n#define __LOGGING_BRIDGE_XLFACILITY__\n\n#import \"XLFacilityMacros.h\"\n\n#define _LOG_DEBUG(...) XLOG_DEBUG(__VA_ARGS__)\n#define _LOG_VERBOSE(...) XLOG_VERBOSE(__VA_ARGS__)\n#define _LOG_INFO(...) XLOG_INFO(__VA_ARGS__)\n#define _LOG_WARNING(...) XLOG_WARNING(__VA_ARGS__)\n#define _LOG_ERROR(...) XLOG_ERROR(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) XLOG_EXCEPTION(__EXCEPTION__)\n\n#define _LOG_DEBUG_CHECK(__CONDITION__) XLOG_DEBUG_CHECK(__CONDITION__)\n#define _LOG_DEBUG_UNREACHABLE() XLOG_DEBUG_UNREACHABLE()\n\n/**\n *  Automatically detect if CocoaLumberJack is available.\n */\n\n#elif defined(__has_include) && __has_include(\"DDLogMacros.h\")\n\n#import \"DDLogMacros.h\"\n\n#define __LOGGING_BRIDGE_COCOALUMBERJACK__\n\n#undef LOG_LEVEL_DEF\n#define LOG_LEVEL_DEF _LoggingMinLevel\nextern int _LoggingMinLevel;\n\n#define _LOG_DEBUG(...) DDLogDebug(__VA_ARGS__)\n#define _LOG_VERBOSE(...) DDLogVerbose(__VA_ARGS__)\n#define _LOG_INFO(...) DDLogInfo(__VA_ARGS__)\n#define _LOG_WARNING(...) DDLogWarn(__VA_ARGS__)\n#define _LOG_ERROR(...) DDLogError(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) DDLogError(@\"%@\", __EXCEPTION__)\n\n/**\n *  Check if a custom logging header should be used instead.\n */\n\n#elif defined(__LOGGING_CUSTOM_HEADER__)\n\n#define __LOGGING_BRIDGE_CUSTOM__\n\n#import __LOGGING_CUSTOM_HEADER__\n\n/**\n *  If all of the above fail, fall back to NSLog().\n */\n\n#else\n\n#define __LOGGING_BRIDGE_BUILTIN__\n\n#if DEBUG\n#define _LOG_DEBUG(...) NSLog(__VA_ARGS__)\n#define _LOG_VERBOSE(...) NSLog(__VA_ARGS__)\n#define _LOG_INFO(...) NSLog(__VA_ARGS__)\n#else\n#define _LOG_DEBUG(...)\n#define _LOG_VERBOSE(...)\n#define _LOG_INFO(...)\n#endif\n#define _LOG_WARNING(...) NSLog(__VA_ARGS__)\n#define _LOG_ERROR(...) NSLog(__VA_ARGS__)\n#define _LOG_EXCEPTION(__EXCEPTION__) NSLog(@\"%@\", __EXCEPTION__)\n\n#endif\n\n/**\n *  Consistency check macros.\n */\n\n#if !defined(_LOG_CHECK)\n#define _LOG_CHECK(__CONDITION__) \\\n  do {                            \\\n    if (!(__CONDITION__)) {       \\\n      abort();                    \\\n    }                             \\\n  } while (0)\n#endif\n\n#if !defined(_LOG_DEBUG_CHECK)\n#if DEBUG\n#define _LOG_DEBUG_CHECK(__CONDITION__) _LOG_CHECK(__CONDITION__)\n#else\n#define _LOG_DEBUG_CHECK(__CONDITION__)\n#endif\n#endif\n\n#if !defined(_LOG_UNREACHABLE)\n#define _LOG_UNREACHABLE() abort()\n#endif\n\n#if !defined(_LOG_DEBUG_UNREACHABLE)\n#if DEBUG\n#define _LOG_DEBUG_UNREACHABLE() _LOG_UNREACHABLE()\n#else\n#define _LOG_DEBUG_UNREACHABLE()\n#endif\n#endif\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetPrivate.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n/**\n *  All GCDTelnetServer headers.\n */\n\n#import \"GCDTelnetServer.h\"\n#import \"GCDTelnetLoggingBridgePrivate.h\"\n\n/**\n *  GCDTelnetServer internal constants and APIs.\n */\n\n// Network Virtual Terminal control codes\ntypedef NS_ENUM(unsigned char, ControlCode) {\n\n  // Required\n  kControlCode_NUL = 0,  // NULL - No operation\n  kControlCode_LF = 10,  // Line Feed - Moves the printer to the next print line, keeping the same horizontal position.\n  kControlCode_CR = 13,  // Carriage Return - Moves the printer to the left margin of the current line.\n\n  // Optional\n  kControlCode_BEL = 7,  // BELL - Produces an audible or visible signal (which does NOT move the print head).\n  kControlCode_BS = 8,  // Back Space - Moves the print head one character position towards the left margin. (On a printing device, this mechanism was commonly used to form composite characters by printing two basic characters on top of each other.)\n  kControlCode_HT = 9,  // Horizontal Tab - Moves the printer to the next horizontal tab stop. It remains unspecified how either party determines or establishes where such tab stops are located.\n  kControlCode_VT = 11,  // Vertical Tab - Moves the printer to the next vertical tab stop. It remains unspecified how either party determines or establishes where such tab stops are located.\n  kControlCode_FF = 12  // Form Feed - Moves the printer to the top of the next page, keeping the same horizontal position. (On visual displays, this commonly clears the screen and moves the cursor to the top left corner.)\n\n};\n\n// Telnet commands\ntypedef NS_ENUM(unsigned char, TelnetCommand) {\n  kTelnetCommand_SE = 240,  // End of subnegotiation parameters\n  kTelnetCommand_NOP = 241,  // No operation\n  kTelnetCommand_DM = 242,  // Data mark - Indicates the position of a Synch event within the data stream. This should always be accompanied by a TCP urgent notification.\n  kTelnetCommand_BRK = 243,  // Break - Indicates that the \"break\" or \"attention\" key was hi.\n  kTelnetCommand_IP = 244,  // Suspend - Interrupt or abort the process to which the NVT is connected.\n  kTelnetCommand_AO = 245,  // Abort output - Allows the current process to run to completion but does not send its output to the user.\n  kTelnetCommand_AYT = 246,  // Are you there - Send back to the NVT some visible evidence that the AYT was received.\n  kTelnetCommand_EC = 247,  // Erase character - The receiver should delete the last preceding undeleted character from the data stream.\n  kTelnetCommand_EL = 248,  // Erase line - Delete characters from the data stream back to but not including the previous CRLF.\n  kTelnetCommand_GA = 249,  // Go ahead - Under certain circumstances used to tell the other end that it can transmit.\n  kTelnetCommand_SB = 250,  // Subnegotiation - Subnegotiation of the indicated option follows.\n  kTelnetCommand_WILL = 251,  // will - Indicates the desire to begin performing, or confirmation that you are now performing, the indicated option.\n  kTelnetCommand_WONT = 252,  // wont - Indicates the refusal to perform, or continue performing, the indicated option.\n  kTelnetCommand_DO = 253,  // do - Indicates the request that the other party perform, or confirmation that you are expecting the other party to perform, the indicated option.\n  kTelnetCommand_DONT = 254,  // dont - Indicates the demand that the other party stop performing, or confirmation that you are no longer expecting the other party to perform, the indicated option.\n  kTelnetCommand_IAC = 255  // Interpret as command - Interpret as a command\n};\n\ntypedef NS_ENUM(unsigned char, TelnetOption) {\n  kTelnetOption_Echo = 1,  // RFC 857\n  kTelnetOption_SuppressGoAhead = 3,  // RFC 858\n  kTelnetOption_Status = 5,  // RFC 859\n  kTelnetOption_TimingMark = 6,  // RFC 860\n  kTelnetOption_TerminalType = 24,  // RFC 1091\n  kTelnetOption_WindowSize = 31,  // RFC 1073\n  kTelnetOption_TerminalSpeed = 32,  // RFC 1079\n  kTelnetOption_RemoteFlowControl = 33,  // RFC 1372\n  kTelnetOption_Linemode = 34,  // RFC 1184\n  kTelnetOption_EnvironmentVariables = 36  // RFC 1408\n};\n\n@interface GCDTelnetServer ()\n@property(nonatomic, readonly) GCDTelnetStartHandler startHandler;\n@property(nonatomic, readonly) GCDTelnetLineHandler lineHandler;\n@end\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetServer.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTelnetConnection.h\"\n\n/**\n *  The GCDTelnetStartHandler is called by the Telnet server whenever a new\n *  connection is open with a remote terminal.\n *\n *  The handler can return a string (or nil) to be sent to the terminal.\n *  Note that the string will be converted to ASCII characters.\n *\n *  @warning This block will be executed on arbitrary threads.\n */\ntypedef NSString* (^GCDTelnetStartHandler)(GCDTelnetConnection* connection);\n\n/**\n *  The GCDTelnetLineHandler is called whenever a new line has been received\n *  from the connected terminal.\n *\n *  The handler can return a string (or nil) to be sent back to the terminal.\n *  Note that the string will be converted to ASCII characters.\n *\n *  @warning This block will be executed on arbitrary threads.\n */\ntypedef NSString* (^GCDTelnetLineHandler)(GCDTelnetConnection* connection, NSString* line);\n\n/**\n *  The GCDTelnetCommandHandler is a special line handler that pre-parses the\n *  line like a command line interface extracting the command and arguments.\n *\n *  @warning This block will be executed on arbitrary threads.\n */\ntypedef NSString* (^GCDTelnetCommandHandler)(GCDTelnetConnection* connection, NSString* command, NSArray* arguments);\n\n/**\n *  The GCDTelnetServer class implements a Telnet server.\n */\n@interface GCDTelnetServer : GCDTCPServer\n\n/**\n *  Initializes a Telnet server on a given port and using the default\n *  GCDTelnetConnection class.\n */\n- (instancetype)initWithPort:(NSUInteger)port startHandler:(GCDTelnetStartHandler)startHandler lineHandler:(GCDTelnetLineHandler)lineHandler;\n\n/**\n *  Initializes a Telnet server on a given port and using the default\n *  GCDTelnetConnection class but with a command handler instead of a line hander.\n */\n- (instancetype)initWithPort:(NSUInteger)port startHandler:(GCDTelnetStartHandler)startHandler commandHandler:(GCDTelnetCommandHandler)commandHandler;\n\n/**\n *  This method is the designated initializer for the class.\n *\n *  Connection class must be [GCDTelnetConnection class] or a subclass of it.\n */\n- (instancetype)initWithConnectionClass:(Class)connectionClass\n                                   port:(NSUInteger)port\n                           startHandler:(GCDTelnetStartHandler)startHandler\n                            lineHandler:(GCDTelnetLineHandler)lineHandler;\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer/GCDTelnetServer.m",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"GCDTelnetPrivate.h\"\n\n/* Information Sources\n \n - http://support.microsoft.com/kb/231866\n - http://pcmicro.com/netfoss/telnet.html\n - http://mud-dev.wikidot.com/telnet:negotiation\n - http://tintin.sourceforge.net/mtts/\n \n */\n\n/* Telnet Option Negotiation\n \n Sender Sent    Receiver Responds     Implication\n WILL           DO                    The sender would like to use a certain facility if the receiver can handle it. Option is now in effect.\n WILL           DONT                  Receiver says it cannot support the option.\tOption is not in effect.\n DO             WILL                  The sender says it can handle traffic from the sender if the sender wishes to use a certain option. Option is now in effect.\n DO             WONT                  Receiver says it cannot support the option. Option is not in effect.\n WONT           DONT                  Option disabled. DONT is only valid response.\n DONT           WONT                  Option disabled. WONT is only valid response.\n \n */\n\n/* Telnet Built-in CLT from OS X 10.10\n \n -> IAC, WILL, Echo,\n <- IAC, DO, Echo,\n \n -> IAC, WILL, Supress Go Ahead,\n <- IAC, DO, Supress Go Ahead,\n \n -> IAC, WILL, Status,\n <- IAC, DO, Status,\n \n (no response for Timing Mark)\n \n -> IAC, WILL, Terminal Type,\n <- IAC, DONT, Terminal Type,\n \n -> IAC, WILL, Window Size,\n <- IAC, DONT, Window Size,\n \n -> IAC, WILL, Terminal Speed,\n <- IAC, DONT, Terminal Speed,\n \n -> IAC, WILL, Remote Flow Control,\n <- IAC, DONT, Remote Flow Control,\n \n -> IAC, WILL, Linemode,\n <- IAC, DONT, Linemode,\n \n -> IAC, WILL, Environment Variables,\n <- IAC, DONT, Environment Variables,\n \n */\n\n/* Telnet Built-in CLT from OS X 10.10\n \n -> IAC, DO, Echo,\n <- IAC, WONT, Echo,\n \n -> IAC, DO, Supress Go Ahead,\n <- IAC, WILL, Supress Go Ahead,\n \n -> IAC, DO, Status,\n <- IAC, WONT, Status,\n \n -> IAC, DO, Timing Mark,\n <- IAC, WILL, Timing Mark,\n \n -> IAC, DO, Terminal Type,\n <- IAC, WILL, Terminal Type,\n \n -> IAC, DO, Window Size,\n <- IAC, WILL, Window Size, IAC, SB, Window Size, 0 208 0 42, IAC, SE,\n \n -> IAC, DO, Terminal Speed,\n <- IAC, WILL, Terminal Speed,\n \n -> IAC, DO, Remote Flow Control,\n <- IAC, WILL, Remote Flow Control,\n \n -> IAC, DO, Linemode,\n <- IAC, DO, Supress Go Ahead, IAC, WILL, Linemode, IAC, SB, Linemode, 3 1 3 0 3 98 3 4 2 15 5 2 20 7 98 28 8 2 4 9 66 26 10 2 127 11 2 21 12 2 23 13 2 18 14 2 22 15 2 17 16 2 19 17 0 255 255 18 0 255 255, IAC, SE,\n \n -> IAC, DO, Environment Variables, \n <- IAC, WONT, Environment Variables,\n \n */\n\n@implementation GCDTelnetServer\n\n- (instancetype)initWithConnectionClass:(Class)connectionClass port:(NSUInteger)port {\n  return [self initWithConnectionClass:connectionClass port:port startHandler:NULL lineHandler:NULL];\n}\n\n- (instancetype)initWithPort:(NSUInteger)port startHandler:(GCDTelnetStartHandler)startHandler lineHandler:(GCDTelnetLineHandler)lineHandler {\n  return [self initWithConnectionClass:[GCDTelnetConnection class] port:port startHandler:startHandler lineHandler:lineHandler];\n}\n\n- (instancetype)initWithPort:(NSUInteger)port startHandler:(GCDTelnetStartHandler)startHandler commandHandler:(GCDTelnetCommandHandler)commandHandler {\n  return [self initWithPort:port\n               startHandler:startHandler\n                lineHandler:^NSString*(GCDTelnetConnection* connection, NSString* line) {\n                  NSArray* array = [connection parseLineAsCommandAndArguments:line];\n                  if (array.count) {\n                    NSString* command = array[0];\n                    NSArray* arguments = [array subarrayWithRange:NSMakeRange(1, array.count - 1)];\n                    return commandHandler(connection, command, arguments);\n                  }\n                  return nil;\n                }];\n}\n\n- (instancetype)initWithConnectionClass:(Class)connectionClass\n                                   port:(NSUInteger)port\n                           startHandler:(GCDTelnetStartHandler)startHandler\n                            lineHandler:(GCDTelnetLineHandler)lineHandler {\n  _LOG_DEBUG_CHECK([connectionClass isSubclassOfClass:[GCDTelnetConnection class]]);\n  if ((self = [super initWithConnectionClass:connectionClass port:port])) {\n    _startHandler = startHandler;\n    _lineHandler = lineHandler;\n  }\n  return self;\n}\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer/NSMutableString+ANSI.h",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <Foundation/Foundation.h>\n\n/**\n *  Constants representing ANSI colors.\n *\n *  See https://en.wikipedia.org/wiki/ANSI_escape_code for details.\n */\ntypedef NS_ENUM(unsigned char, ANSIColor) {\n  kANSIColor_Black = 0,\n  kANSIColor_Red,\n  kANSIColor_Green,\n  kANSIColor_Yellow,\n  kANSIColor_Blue,\n  kANSIColor_Magenta,\n  kANSIColor_Cyan,\n  kANSIColor_White\n};\n\n/**\n *  Extensions to NSMutableString to create ANSI colored strings.\n */\n@interface NSMutableString (ANSI)\n\n/**\n *  Appends a string using the provided ANSI color and optionally in bold.\n */\n- (void)appendANSIString:(NSString*)string withColor:(ANSIColor)color bold:(BOOL)bold;\n\n/**\n *  Appends a formatted string using the provided ANSI color and optionally in bold.\n */\n- (void)appendANSIStringWithColor:(ANSIColor)color bold:(BOOL)bold format:(NSString*)format, ... NS_FORMAT_FUNCTION(3, 4);\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer/NSMutableString+ANSI.m",
    "content": "/*\n Copyright (c) 2012-2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"NSMutableString+ANSI.h\"\n\n#define kCSIPrefix \"\\x1b[\"\n\n@implementation NSMutableString (ANSI)\n\n- (void)appendANSIString:(NSString*)string withColor:(ANSIColor)color bold:(BOOL)bold {\n  [self appendFormat:@\"%s%i%sm%@%s0m\", kCSIPrefix, 30 + color, bold ? \";1\" : \"\", string, kCSIPrefix];\n}\n\n- (void)appendANSIStringWithColor:(ANSIColor)color bold:(BOOL)bold format:(NSString*)format, ... {\n  va_list arguments;\n  va_start(arguments, format);\n  NSString* string = [[NSMutableString alloc] initWithFormat:format arguments:arguments];\n  va_end(arguments);\n  [self appendANSIString:string withColor:color bold:bold];\n}\n\n@end\n"
  },
  {
    "path": "GCDTelnetServer.podspec",
    "content": "# http://guides.cocoapods.org/syntax/podspec.html\n# http://guides.cocoapods.org/making/getting-setup-with-trunk.html\n# $ sudo gem update cocoapods\n# (optional) $ pod trunk register {email} {name} --description={computer}\n# $ pod trunk --verbose push\n# DELETE THIS SECTION BEFORE PROCEEDING!\n\nPod::Spec.new do |s|\n  s.name     = 'GCDTelnetServer'\n  s.version  = '1.1.6'\n  s.author   =  { 'Pierre-Olivier Latour' => 'info@pol-online.net' }\n  s.license  = { :type => 'BSD', :file => 'LICENSE' }\n  s.homepage = 'https://github.com/swisspol/GCDTelnetServer'\n  s.summary  = 'Drop-in embedded Telnet server for iOS and OS X apps'\n\n  s.source   = { :git => 'https://github.com/swisspol/GCDTelnetServer.git', :tag => s.version.to_s }\n  s.ios.deployment_target = '8.0'\n  s.osx.deployment_target = '10.8'\n  s.requires_arc = true\n\n  s.subspec 'GCDNetworking' do |cs|\n    cs.source_files = 'GCDNetworking/GCDNetworking/*.{h,m}'\n    cs.private_header_files = \"GCDNetworking/GCDNetworking/*Private.h\"\n    cs.requires_arc = true\n    cs.osx.frameworks = 'SystemConfiguration'\n    cs.ios.frameworks = 'CFNetwork'\n  end\n\n  s.subspec 'Core' do |cs|\n    cs.dependency 'GCDTelnetServer/GCDNetworking'\n    s.source_files = 'GCDTelnetServer/*.{h,m}'\n    s.private_header_files = \"GCDTelnetServer/*Private.h\"\n    cs.requires_arc = true\n  end\n\nend\n"
  },
  {
    "path": "GCDTelnetServer.xcodeproj/project.pbxproj",
    "content": "// !$*UTF8*$!\n{\n\tarchiveVersion = 1;\n\tclasses = {\n\t};\n\tobjectVersion = 48;\n\tobjects = {\n\n/* Begin PBXAggregateTarget section */\n\t\tE2B3CEE619E91770003ED065 /* Build All */ = {\n\t\t\tisa = PBXAggregateTarget;\n\t\t\tbuildConfigurationList = E2B3CEE719E91770003ED065 /* Build configuration list for PBXAggregateTarget \"Build All\" */;\n\t\t\tbuildPhases = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t\tE2B3CEEB19E91784003ED065 /* PBXTargetDependency */,\n\t\t\t\tE2B3CF2B19E9189C003ED065 /* PBXTargetDependency */,\n\t\t\t\tE2168F9619EE04B200865350 /* PBXTargetDependency */,\n\t\t\t);\n\t\t\tname = \"Build All\";\n\t\t\tproductName = \"Build All\";\n\t\t};\n/* End PBXAggregateTarget section */\n\n/* Begin PBXBuildFile section */\n\t\tE26ABC2C19EC9F9A00654D9F /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = E26ABC2B19EC9F9A00654D9F /* main.m */; };\n\t\tE280BF1419E9FF5000D85595 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1319E9FF5000D85595 /* CFNetwork.framework */; };\n\t\tE280BF1619E9FF5500D85595 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1519E9FF5500D85595 /* CFNetwork.framework */; };\n\t\tE295AF901E6B4C5E00EAC2FF /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E295AF8F1E6B4C5E00EAC2FF /* SystemConfiguration.framework */; };\n\t\tE295AF911E6B4C6800EAC2FF /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E295AF8F1E6B4C5E00EAC2FF /* SystemConfiguration.framework */; };\n\t\tE298C47A19ED866100C76821 /* GCDTelnetServer_Tests.m in Sources */ = {isa = PBXBuildFile; fileRef = E298C47919ED866100C76821 /* GCDTelnetServer_Tests.m */; };\n\t\tE298C48619ED892500C76821 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E280BF1319E9FF5000D85595 /* CFNetwork.framework */; };\n\t\tE2B03DCD19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03DCC19F4659F00D56CA6 /* GCDTelnetServer.m */; };\n\t\tE2B03DCE19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03DCC19F4659F00D56CA6 /* GCDTelnetServer.m */; };\n\t\tE2B03DCF19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03DCC19F4659F00D56CA6 /* GCDTelnetServer.m */; };\n\t\tE2B03E0919F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0819F46A7300D56CA6 /* NSMutableString+ANSI.m */; };\n\t\tE2B03E0A19F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0819F46A7300D56CA6 /* NSMutableString+ANSI.m */; };\n\t\tE2B03E0B19F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0819F46A7300D56CA6 /* NSMutableString+ANSI.m */; };\n\t\tE2B03E0E19F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0D19F46B1C00D56CA6 /* GCDTelnetConnection.m */; };\n\t\tE2B03E0F19F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0D19F46B1C00D56CA6 /* GCDTelnetConnection.m */; };\n\t\tE2B03E1019F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E0D19F46B1C00D56CA6 /* GCDTelnetConnection.m */; };\n\t\tE2B03E8719F49EAD00D56CA6 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8019F49EAD00D56CA6 /* GCDTCPClient.m */; };\n\t\tE2B03E8819F49EAD00D56CA6 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8019F49EAD00D56CA6 /* GCDTCPClient.m */; };\n\t\tE2B03E8919F49EAD00D56CA6 /* GCDTCPClient.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8019F49EAD00D56CA6 /* GCDTCPClient.m */; };\n\t\tE2B03E8A19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8219F49EAD00D56CA6 /* GCDTCPConnection.m */; };\n\t\tE2B03E8B19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8219F49EAD00D56CA6 /* GCDTCPConnection.m */; };\n\t\tE2B03E8C19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8219F49EAD00D56CA6 /* GCDTCPConnection.m */; };\n\t\tE2B03E8D19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8419F49EAD00D56CA6 /* GCDTCPPeer.m */; };\n\t\tE2B03E8E19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8419F49EAD00D56CA6 /* GCDTCPPeer.m */; };\n\t\tE2B03E8F19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8419F49EAD00D56CA6 /* GCDTCPPeer.m */; };\n\t\tE2B03E9019F49EAD00D56CA6 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8619F49EAD00D56CA6 /* GCDTCPServer.m */; };\n\t\tE2B03E9119F49EAD00D56CA6 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8619F49EAD00D56CA6 /* GCDTCPServer.m */; };\n\t\tE2B03E9219F49EAD00D56CA6 /* GCDTCPServer.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B03E8619F49EAD00D56CA6 /* GCDTCPServer.m */; };\n\t\tE2B3CF1B19E91825003ED065 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B3CF1819E91825003ED065 /* AppDelegate.m */; };\n\t\tE2B3CF1D19E91825003ED065 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = E2B3CF1A19E91825003ED065 /* main.m */; };\n\t\tE2B3CF3019E919DD003ED065 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = E2B3CF2F19E919DD003ED065 /* UIKit.framework */; };\n/* End PBXBuildFile section */\n\n/* Begin PBXContainerItemProxy section */\n\t\tE2168F9519EE04B200865350 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E298C46B19ED859F00C76821;\n\t\t\tremoteInfo = \"XLFacility (Tests)\";\n\t\t};\n\t\tE2B3CEEA19E91784003ED065 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E26DC16619E8494700C68DDC;\n\t\t\tremoteInfo = GCDLogger;\n\t\t};\n\t\tE2B3CF2A19E9189C003ED065 /* PBXContainerItemProxy */ = {\n\t\t\tisa = PBXContainerItemProxy;\n\t\t\tcontainerPortal = E26DC15F19E8494700C68DDC /* Project object */;\n\t\t\tproxyType = 1;\n\t\t\tremoteGlobalIDString = E2B3CEEF19E917BB003ED065;\n\t\t\tremoteInfo = \"GCDLogger (iOS)\";\n\t\t};\n/* End PBXContainerItemProxy section */\n\n/* Begin PBXFileReference section */\n\t\tE26ABC2B19EC9F9A00654D9F /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = \"<group>\"; };\n\t\tE26DC16719E8494700C68DDC /* GCDTelnetServer */ = {isa = PBXFileReference; explicitFileType = \"compiled.mach-o.executable\"; includeInIndex = 0; path = GCDTelnetServer; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE280BF0E19E9F3DF00D85595 /* README.md */ = {isa = PBXFileReference; lastKnownFileType = net.daringfireball.markdown; path = README.md; sourceTree = \"<group>\"; };\n\t\tE280BF1319E9FF5000D85595 /* CFNetwork.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CFNetwork.framework; path = System/Library/Frameworks/CFNetwork.framework; sourceTree = SDKROOT; };\n\t\tE280BF1519E9FF5500D85595 /* CFNetwork.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CFNetwork.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS8.1.sdk/System/Library/Frameworks/CFNetwork.framework; sourceTree = DEVELOPER_DIR; };\n\t\tE295AF8F1E6B4C5E00EAC2FF /* SystemConfiguration.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SystemConfiguration.framework; path = System/Library/Frameworks/SystemConfiguration.framework; sourceTree = SDKROOT; };\n\t\tE298C46C19ED859F00C76821 /* Tests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = Tests.xctest; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE298C47919ED866100C76821 /* GCDTelnetServer_Tests.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTelnetServer_Tests.m; sourceTree = \"<group>\"; };\n\t\tE2B03DCB19F4659F00D56CA6 /* GCDTelnetServer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTelnetServer.h; sourceTree = \"<group>\"; };\n\t\tE2B03DCC19F4659F00D56CA6 /* GCDTelnetServer.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTelnetServer.m; sourceTree = \"<group>\"; };\n\t\tE2B03DD019F465E100D56CA6 /* GCDTelnetServer.podspec */ = {isa = PBXFileReference; lastKnownFileType = text; path = GCDTelnetServer.podspec; sourceTree = \"<group>\"; };\n\t\tE2B03E0719F46A7300D56CA6 /* NSMutableString+ANSI.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = \"NSMutableString+ANSI.h\"; sourceTree = \"<group>\"; };\n\t\tE2B03E0819F46A7300D56CA6 /* NSMutableString+ANSI.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = \"NSMutableString+ANSI.m\"; sourceTree = \"<group>\"; };\n\t\tE2B03E0C19F46B1C00D56CA6 /* GCDTelnetConnection.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTelnetConnection.h; sourceTree = \"<group>\"; };\n\t\tE2B03E0D19F46B1C00D56CA6 /* GCDTelnetConnection.m */ = {isa = PBXFileReference; fileEncoding = 4; indentWidth = 2; lastKnownFileType = sourcecode.c.objc; path = GCDTelnetConnection.m; sourceTree = \"<group>\"; tabWidth = 2; };\n\t\tE2B03E1119F46BBB00D56CA6 /* GCDTelnetPrivate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GCDTelnetPrivate.h; sourceTree = \"<group>\"; };\n\t\tE2B03E3919F4939000D56CA6 /* GCDTelnetLoggingBridgePrivate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = GCDTelnetLoggingBridgePrivate.h; sourceTree = \"<group>\"; };\n\t\tE2B03E7C19F49EAD00D56CA6 /* GCDNetworkingLoggingBridgePrivate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDNetworkingLoggingBridgePrivate.h; sourceTree = \"<group>\"; };\n\t\tE2B03E7D19F49EAD00D56CA6 /* GCDNetworking.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDNetworking.h; sourceTree = \"<group>\"; };\n\t\tE2B03E7E19F49EAD00D56CA6 /* GCDNetworkingPrivate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDNetworkingPrivate.h; sourceTree = \"<group>\"; };\n\t\tE2B03E7F19F49EAD00D56CA6 /* GCDTCPClient.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPClient.h; sourceTree = \"<group>\"; };\n\t\tE2B03E8019F49EAD00D56CA6 /* GCDTCPClient.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPClient.m; sourceTree = \"<group>\"; };\n\t\tE2B03E8119F49EAD00D56CA6 /* GCDTCPConnection.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPConnection.h; sourceTree = \"<group>\"; };\n\t\tE2B03E8219F49EAD00D56CA6 /* GCDTCPConnection.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPConnection.m; sourceTree = \"<group>\"; };\n\t\tE2B03E8319F49EAD00D56CA6 /* GCDTCPPeer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPPeer.h; sourceTree = \"<group>\"; };\n\t\tE2B03E8419F49EAD00D56CA6 /* GCDTCPPeer.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPPeer.m; sourceTree = \"<group>\"; };\n\t\tE2B03E8519F49EAD00D56CA6 /* GCDTCPServer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = GCDTCPServer.h; sourceTree = \"<group>\"; };\n\t\tE2B03E8619F49EAD00D56CA6 /* GCDTCPServer.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = GCDTCPServer.m; sourceTree = \"<group>\"; };\n\t\tE2B3CEF019E917BB003ED065 /* GCDTelnetServer.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = GCDTelnetServer.app; sourceTree = BUILT_PRODUCTS_DIR; };\n\t\tE2B3CF1719E91825003ED065 /* AppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = \"<group>\"; };\n\t\tE2B3CF1819E91825003ED065 /* AppDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = \"<group>\"; };\n\t\tE2B3CF1919E91825003ED065 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = \"<group>\"; };\n\t\tE2B3CF1A19E91825003ED065 /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = \"<group>\"; };\n\t\tE2B3CF2F19E919DD003ED065 /* UIKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = UIKit.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS8.1.sdk/System/Library/Frameworks/UIKit.framework; sourceTree = DEVELOPER_DIR; };\n/* End PBXFileReference section */\n\n/* Begin PBXFrameworksBuildPhase section */\n\t\tE26DC16419E8494700C68DDC /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE295AF901E6B4C5E00EAC2FF /* SystemConfiguration.framework in Frameworks */,\n\t\t\t\tE280BF1419E9FF5000D85595 /* CFNetwork.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE298C46919ED859F00C76821 /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE295AF911E6B4C6800EAC2FF /* SystemConfiguration.framework in Frameworks */,\n\t\t\t\tE298C48619ED892500C76821 /* CFNetwork.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE2B3CEED19E917BB003ED065 /* Frameworks */ = {\n\t\t\tisa = PBXFrameworksBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE280BF1619E9FF5500D85595 /* CFNetwork.framework in Frameworks */,\n\t\t\t\tE2B3CF3019E919DD003ED065 /* UIKit.framework in Frameworks */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXFrameworksBuildPhase section */\n\n/* Begin PBXGroup section */\n\t\tE26ABC2A19EC9F9A00654D9F /* CLT */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE26ABC2B19EC9F9A00654D9F /* main.m */,\n\t\t\t);\n\t\t\tpath = CLT;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE26DC15E19E8494700C68DDC = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE280BF0E19E9F3DF00D85595 /* README.md */,\n\t\t\t\tE2B03DD019F465E100D56CA6 /* GCDTelnetServer.podspec */,\n\t\t\t\tE2B03DCA19F4659F00D56CA6 /* GCDTelnetServer */,\n\t\t\t\tE26ABC2A19EC9F9A00654D9F /* CLT */,\n\t\t\t\tE2B3CF1619E91825003ED065 /* iOS */,\n\t\t\t\tE298C47719ED866100C76821 /* Tests */,\n\t\t\t\tE2B03E7B19F49EAD00D56CA6 /* GCDNetworking */,\n\t\t\t\tE26DC19E19E883CC00C68DDC /* Mac Frameworks and Libraries */,\n\t\t\t\tE2B3CF2E19E919AC003ED065 /* iOS Frameworks and Libraries */,\n\t\t\t\tE26DC16819E8494700C68DDC /* Products */,\n\t\t\t);\n\t\t\tindentWidth = 2;\n\t\t\tsourceTree = \"<group>\";\n\t\t\ttabWidth = 2;\n\t\t};\n\t\tE26DC16819E8494700C68DDC /* Products */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE26DC16719E8494700C68DDC /* GCDTelnetServer */,\n\t\t\t\tE2B3CEF019E917BB003ED065 /* GCDTelnetServer.app */,\n\t\t\t\tE298C46C19ED859F00C76821 /* Tests.xctest */,\n\t\t\t);\n\t\t\tname = Products;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE26DC19E19E883CC00C68DDC /* Mac Frameworks and Libraries */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE295AF8F1E6B4C5E00EAC2FF /* SystemConfiguration.framework */,\n\t\t\t\tE280BF1319E9FF5000D85595 /* CFNetwork.framework */,\n\t\t\t);\n\t\t\tname = \"Mac Frameworks and Libraries\";\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE298C47719ED866100C76821 /* Tests */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE298C47919ED866100C76821 /* GCDTelnetServer_Tests.m */,\n\t\t\t);\n\t\t\tpath = Tests;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B03DCA19F4659F00D56CA6 /* GCDTelnetServer */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B03E0C19F46B1C00D56CA6 /* GCDTelnetConnection.h */,\n\t\t\t\tE2B03E0D19F46B1C00D56CA6 /* GCDTelnetConnection.m */,\n\t\t\t\tE2B03E1119F46BBB00D56CA6 /* GCDTelnetPrivate.h */,\n\t\t\t\tE2B03E3919F4939000D56CA6 /* GCDTelnetLoggingBridgePrivate.h */,\n\t\t\t\tE2B03DCB19F4659F00D56CA6 /* GCDTelnetServer.h */,\n\t\t\t\tE2B03DCC19F4659F00D56CA6 /* GCDTelnetServer.m */,\n\t\t\t\tE2B03E0719F46A7300D56CA6 /* NSMutableString+ANSI.h */,\n\t\t\t\tE2B03E0819F46A7300D56CA6 /* NSMutableString+ANSI.m */,\n\t\t\t);\n\t\t\tpath = GCDTelnetServer;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B03E7B19F49EAD00D56CA6 /* GCDNetworking */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B03E7D19F49EAD00D56CA6 /* GCDNetworking.h */,\n\t\t\t\tE2B03E7E19F49EAD00D56CA6 /* GCDNetworkingPrivate.h */,\n\t\t\t\tE2B03E7C19F49EAD00D56CA6 /* GCDNetworkingLoggingBridgePrivate.h */,\n\t\t\t\tE2B03E7F19F49EAD00D56CA6 /* GCDTCPClient.h */,\n\t\t\t\tE2B03E8019F49EAD00D56CA6 /* GCDTCPClient.m */,\n\t\t\t\tE2B03E8119F49EAD00D56CA6 /* GCDTCPConnection.h */,\n\t\t\t\tE2B03E8219F49EAD00D56CA6 /* GCDTCPConnection.m */,\n\t\t\t\tE2B03E8319F49EAD00D56CA6 /* GCDTCPPeer.h */,\n\t\t\t\tE2B03E8419F49EAD00D56CA6 /* GCDTCPPeer.m */,\n\t\t\t\tE2B03E8519F49EAD00D56CA6 /* GCDTCPServer.h */,\n\t\t\t\tE2B03E8619F49EAD00D56CA6 /* GCDTCPServer.m */,\n\t\t\t);\n\t\t\tname = GCDNetworking;\n\t\t\tpath = GCDNetworking/GCDNetworking;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B3CF1619E91825003ED065 /* iOS */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B3CF1719E91825003ED065 /* AppDelegate.h */,\n\t\t\t\tE2B3CF1819E91825003ED065 /* AppDelegate.m */,\n\t\t\t\tE2B3CF1919E91825003ED065 /* Info.plist */,\n\t\t\t\tE2B3CF1A19E91825003ED065 /* main.m */,\n\t\t\t);\n\t\t\tpath = iOS;\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n\t\tE2B3CF2E19E919AC003ED065 /* iOS Frameworks and Libraries */ = {\n\t\t\tisa = PBXGroup;\n\t\t\tchildren = (\n\t\t\t\tE2B3CF2F19E919DD003ED065 /* UIKit.framework */,\n\t\t\t\tE280BF1519E9FF5500D85595 /* CFNetwork.framework */,\n\t\t\t);\n\t\t\tname = \"iOS Frameworks and Libraries\";\n\t\t\tsourceTree = \"<group>\";\n\t\t};\n/* End PBXGroup section */\n\n/* Begin PBXNativeTarget section */\n\t\tE26DC16619E8494700C68DDC /* GCDTelnetServer (CLT) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E26DC16E19E8494700C68DDC /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (CLT)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE26DC16319E8494700C68DDC /* Sources */,\n\t\t\t\tE26DC16419E8494700C68DDC /* Frameworks */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDTelnetServer (CLT)\";\n\t\t\tproductName = Logger;\n\t\t\tproductReference = E26DC16719E8494700C68DDC /* GCDTelnetServer */;\n\t\t\tproductType = \"com.apple.product-type.tool\";\n\t\t};\n\t\tE298C46B19ED859F00C76821 /* GCDTelnetServer (Tests) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E298C47619ED859F00C76821 /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (Tests)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE298C46819ED859F00C76821 /* Sources */,\n\t\t\t\tE298C46919ED859F00C76821 /* Frameworks */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDTelnetServer (Tests)\";\n\t\t\tproductName = \"XLFacility Tests\";\n\t\t\tproductReference = E298C46C19ED859F00C76821 /* Tests.xctest */;\n\t\t\tproductType = \"com.apple.product-type.bundle.unit-test\";\n\t\t};\n\t\tE2B3CEEF19E917BB003ED065 /* GCDTelnetServer (iOS) */ = {\n\t\t\tisa = PBXNativeTarget;\n\t\t\tbuildConfigurationList = E2B3CF1019E917BC003ED065 /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (iOS)\" */;\n\t\t\tbuildPhases = (\n\t\t\t\tE2B3CEEC19E917BB003ED065 /* Sources */,\n\t\t\t\tE2B3CEED19E917BB003ED065 /* Frameworks */,\n\t\t\t\tE2B3CEEE19E917BB003ED065 /* Resources */,\n\t\t\t);\n\t\t\tbuildRules = (\n\t\t\t);\n\t\t\tdependencies = (\n\t\t\t);\n\t\t\tname = \"GCDTelnetServer (iOS)\";\n\t\t\tproductName = GCDLogger;\n\t\t\tproductReference = E2B3CEF019E917BB003ED065 /* GCDTelnetServer.app */;\n\t\t\tproductType = \"com.apple.product-type.application\";\n\t\t};\n/* End PBXNativeTarget section */\n\n/* Begin PBXProject section */\n\t\tE26DC15F19E8494700C68DDC /* Project object */ = {\n\t\t\tisa = PBXProject;\n\t\t\tattributes = {\n\t\t\t\tLastUpgradeCheck = 0830;\n\t\t\t\tORGANIZATIONNAME = \"\";\n\t\t\t\tTargetAttributes = {\n\t\t\t\t\tE26DC16619E8494700C68DDC = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t\tE298C46B19ED859F00C76821 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t\tTestTargetID = E26ABC0919EC9E2D00654D9F;\n\t\t\t\t\t};\n\t\t\t\t\tE2B3CEE619E91770003ED065 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t\tE2B3CEEF19E917BB003ED065 = {\n\t\t\t\t\t\tCreatedOnToolsVersion = 6.1;\n\t\t\t\t\t};\n\t\t\t\t};\n\t\t\t};\n\t\t\tbuildConfigurationList = E26DC16219E8494700C68DDC /* Build configuration list for PBXProject \"GCDTelnetServer\" */;\n\t\t\tcompatibilityVersion = \"Xcode 8.0\";\n\t\t\tdevelopmentRegion = English;\n\t\t\thasScannedForEncodings = 0;\n\t\t\tknownRegions = (\n\t\t\t\ten,\n\t\t\t\tBase,\n\t\t\t);\n\t\t\tmainGroup = E26DC15E19E8494700C68DDC;\n\t\t\tproductRefGroup = E26DC16819E8494700C68DDC /* Products */;\n\t\t\tprojectDirPath = \"\";\n\t\t\tprojectRoot = \"\";\n\t\t\ttargets = (\n\t\t\t\tE2B3CEE619E91770003ED065 /* Build All */,\n\t\t\t\tE26DC16619E8494700C68DDC /* GCDTelnetServer (CLT) */,\n\t\t\t\tE2B3CEEF19E917BB003ED065 /* GCDTelnetServer (iOS) */,\n\t\t\t\tE298C46B19ED859F00C76821 /* GCDTelnetServer (Tests) */,\n\t\t\t);\n\t\t};\n/* End PBXProject section */\n\n/* Begin PBXResourcesBuildPhase section */\n\t\tE2B3CEEE19E917BB003ED065 /* Resources */ = {\n\t\t\tisa = PBXResourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXResourcesBuildPhase section */\n\n/* Begin PBXSourcesBuildPhase section */\n\t\tE26DC16319E8494700C68DDC /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2B03E8D19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE2B03E0919F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */,\n\t\t\t\tE26ABC2C19EC9F9A00654D9F /* main.m in Sources */,\n\t\t\t\tE2B03E8A19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */,\n\t\t\t\tE2B03E8719F49EAD00D56CA6 /* GCDTCPClient.m in Sources */,\n\t\t\t\tE2B03E9019F49EAD00D56CA6 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2B03E0E19F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */,\n\t\t\t\tE2B03DCD19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE298C46819ED859F00C76821 /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2B03E8F19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE2B03E0B19F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */,\n\t\t\t\tE298C47A19ED866100C76821 /* GCDTelnetServer_Tests.m in Sources */,\n\t\t\t\tE2B03E8C19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */,\n\t\t\t\tE2B03E8919F49EAD00D56CA6 /* GCDTCPClient.m in Sources */,\n\t\t\t\tE2B03E9219F49EAD00D56CA6 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2B03E1019F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */,\n\t\t\t\tE2B03DCF19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n\t\tE2B3CEEC19E917BB003ED065 /* Sources */ = {\n\t\t\tisa = PBXSourcesBuildPhase;\n\t\t\tbuildActionMask = 2147483647;\n\t\t\tfiles = (\n\t\t\t\tE2B03E8E19F49EAD00D56CA6 /* GCDTCPPeer.m in Sources */,\n\t\t\t\tE2B03E9119F49EAD00D56CA6 /* GCDTCPServer.m in Sources */,\n\t\t\t\tE2B03E0F19F46B1C00D56CA6 /* GCDTelnetConnection.m in Sources */,\n\t\t\t\tE2B3CF1D19E91825003ED065 /* main.m in Sources */,\n\t\t\t\tE2B3CF1B19E91825003ED065 /* AppDelegate.m in Sources */,\n\t\t\t\tE2B03E8B19F49EAD00D56CA6 /* GCDTCPConnection.m in Sources */,\n\t\t\t\tE2B03E0A19F46A7300D56CA6 /* NSMutableString+ANSI.m in Sources */,\n\t\t\t\tE2B03DCE19F4659F00D56CA6 /* GCDTelnetServer.m in Sources */,\n\t\t\t\tE2B03E8819F49EAD00D56CA6 /* GCDTCPClient.m in Sources */,\n\t\t\t);\n\t\t\trunOnlyForDeploymentPostprocessing = 0;\n\t\t};\n/* End PBXSourcesBuildPhase section */\n\n/* Begin PBXTargetDependency section */\n\t\tE2168F9619EE04B200865350 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E298C46B19ED859F00C76821 /* GCDTelnetServer (Tests) */;\n\t\t\ttargetProxy = E2168F9519EE04B200865350 /* PBXContainerItemProxy */;\n\t\t};\n\t\tE2B3CEEB19E91784003ED065 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E26DC16619E8494700C68DDC /* GCDTelnetServer (CLT) */;\n\t\t\ttargetProxy = E2B3CEEA19E91784003ED065 /* PBXContainerItemProxy */;\n\t\t};\n\t\tE2B3CF2B19E9189C003ED065 /* PBXTargetDependency */ = {\n\t\t\tisa = PBXTargetDependency;\n\t\t\ttarget = E2B3CEEF19E917BB003ED065 /* GCDTelnetServer (iOS) */;\n\t\t\ttargetProxy = E2B3CF2A19E9189C003ED065 /* PBXContainerItemProxy */;\n\t\t};\n/* End PBXTargetDependency section */\n\n/* Begin XCBuildConfiguration section */\n\t\tE26DC16C19E8494700C68DDC /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tALWAYS_SEARCH_USER_PATHS = NO;\n\t\t\t\tCLANG_ENABLE_OBJC_ARC = YES;\n\t\t\t\tENABLE_STRICT_OBJC_MSGSEND = YES;\n\t\t\t\tGCC_C_LANGUAGE_STANDARD = gnu99;\n\t\t\t\tGCC_OPTIMIZATION_LEVEL = 0;\n\t\t\t\tGCC_PREPROCESSOR_DEFINITIONS = \"DEBUG=1\";\n\t\t\t\tONLY_ACTIVE_ARCH = YES;\n\t\t\t\tWARNING_CFLAGS = (\n\t\t\t\t\t\"-Wall\",\n\t\t\t\t\t\"-Weverything\",\n\t\t\t\t\t\"-Wshadow\",\n\t\t\t\t\t\"-Wshorten-64-to-32\",\n\t\t\t\t\t\"-Wno-direct-ivar-access\",\n\t\t\t\t\t\"-Wno-objc-missing-property-synthesis\",\n\t\t\t\t\t\"-Wno-implicit-retain-self\",\n\t\t\t\t\t\"-Wno-documentation-unknown-command\",\n\t\t\t\t\t\"-Wno-gnu-statement-expression\",\n\t\t\t\t\t\"-Wno-assign-enum\",\n\t\t\t\t\t\"-Wno-reserved-id-macro\",\n\t\t\t\t\t\"-Wno-cstring-format-directive\",\n\t\t\t\t\t\"-Wno-partial-availability\",\n\t\t\t\t);\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE26DC16D19E8494700C68DDC /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tALWAYS_SEARCH_USER_PATHS = NO;\n\t\t\t\tCLANG_ENABLE_OBJC_ARC = YES;\n\t\t\t\tDEBUG_INFORMATION_FORMAT = \"dwarf-with-dsym\";\n\t\t\t\tENABLE_STRICT_OBJC_MSGSEND = YES;\n\t\t\t\tGCC_C_LANGUAGE_STANDARD = gnu99;\n\t\t\t\tGCC_TREAT_WARNINGS_AS_ERRORS = YES;\n\t\t\t\tWARNING_CFLAGS = \"-Wall\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE26DC16F19E8494700C68DDC /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = GCDTelnetServer;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE26DC17019E8494700C68DDC /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = GCDTelnetServer;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE298C47419ED859F00C76821 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tFRAMEWORK_SEARCH_PATHS = (\n\t\t\t\t\t\"$(DEVELOPER_FRAMEWORKS_DIR)\",\n\t\t\t\t\t\"$(inherited)\",\n\t\t\t\t);\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = Tests;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE298C47519ED859F00C76821 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tFRAMEWORK_SEARCH_PATHS = (\n\t\t\t\t\t\"$(DEVELOPER_FRAMEWORKS_DIR)\",\n\t\t\t\t\t\"$(inherited)\",\n\t\t\t\t);\n\t\t\t\tMACOSX_DEPLOYMENT_TARGET = 10.8;\n\t\t\t\tPRODUCT_NAME = Tests;\n\t\t\t\tSDKROOT = macosx;\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE2B3CEE819E91770003ED065 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tPRODUCT_NAME = \"$(TARGET_NAME)\";\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE2B3CEE919E91770003ED065 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tPRODUCT_NAME = \"$(TARGET_NAME)\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n\t\tE2B3CF1119E917BC003ED065 /* Debug */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tCODE_SIGN_IDENTITY = \"iPhone Developer\";\n\t\t\t\tDEVELOPMENT_TEAM = 88W3E55T4B;\n\t\t\t\tINFOPLIST_FILE = iOS/Info.plist;\n\t\t\t\tIPHONEOS_DEPLOYMENT_TARGET = 8.0;\n\t\t\t\tPRODUCT_NAME = GCDTelnetServer;\n\t\t\t\tSDKROOT = iphoneos;\n\t\t\t\tTARGETED_DEVICE_FAMILY = \"1,2\";\n\t\t\t};\n\t\t\tname = Debug;\n\t\t};\n\t\tE2B3CF1219E917BC003ED065 /* Release */ = {\n\t\t\tisa = XCBuildConfiguration;\n\t\t\tbuildSettings = {\n\t\t\t\tCODE_SIGN_IDENTITY = \"iPhone Developer\";\n\t\t\t\tDEVELOPMENT_TEAM = 88W3E55T4B;\n\t\t\t\tINFOPLIST_FILE = iOS/Info.plist;\n\t\t\t\tIPHONEOS_DEPLOYMENT_TARGET = 8.0;\n\t\t\t\tPRODUCT_NAME = GCDTelnetServer;\n\t\t\t\tSDKROOT = iphoneos;\n\t\t\t\tTARGETED_DEVICE_FAMILY = \"1,2\";\n\t\t\t};\n\t\t\tname = Release;\n\t\t};\n/* End XCBuildConfiguration section */\n\n/* Begin XCConfigurationList section */\n\t\tE26DC16219E8494700C68DDC /* Build configuration list for PBXProject \"GCDTelnetServer\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE26DC16C19E8494700C68DDC /* Debug */,\n\t\t\t\tE26DC16D19E8494700C68DDC /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE26DC16E19E8494700C68DDC /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (CLT)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE26DC16F19E8494700C68DDC /* Debug */,\n\t\t\t\tE26DC17019E8494700C68DDC /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE298C47619ED859F00C76821 /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (Tests)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE298C47419ED859F00C76821 /* Debug */,\n\t\t\t\tE298C47519ED859F00C76821 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE2B3CEE719E91770003ED065 /* Build configuration list for PBXAggregateTarget \"Build All\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE2B3CEE819E91770003ED065 /* Debug */,\n\t\t\t\tE2B3CEE919E91770003ED065 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n\t\tE2B3CF1019E917BC003ED065 /* Build configuration list for PBXNativeTarget \"GCDTelnetServer (iOS)\" */ = {\n\t\t\tisa = XCConfigurationList;\n\t\t\tbuildConfigurations = (\n\t\t\t\tE2B3CF1119E917BC003ED065 /* Debug */,\n\t\t\t\tE2B3CF1219E917BC003ED065 /* Release */,\n\t\t\t);\n\t\t\tdefaultConfigurationIsVisible = 0;\n\t\t\tdefaultConfigurationName = Release;\n\t\t};\n/* End XCConfigurationList section */\n\t};\n\trootObject = E26DC15F19E8494700C68DDC /* Project object */;\n}\n"
  },
  {
    "path": "GCDTelnetServer.xcodeproj/xcshareddata/xcschemes/Tests.xcscheme",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Scheme\n   LastUpgradeVersion = \"0830\"\n   version = \"1.3\">\n   <BuildAction\n      parallelizeBuildables = \"YES\"\n      buildImplicitDependencies = \"YES\">\n      <BuildActionEntries>\n         <BuildActionEntry\n            buildForTesting = \"YES\"\n            buildForRunning = \"NO\"\n            buildForProfiling = \"NO\"\n            buildForArchiving = \"NO\"\n            buildForAnalyzing = \"NO\">\n            <BuildableReference\n               BuildableIdentifier = \"primary\"\n               BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n               BuildableName = \"Tests.xctest\"\n               BlueprintName = \"GCDTelnetServer (Tests)\"\n               ReferencedContainer = \"container:GCDTelnetServer.xcodeproj\">\n            </BuildableReference>\n         </BuildActionEntry>\n      </BuildActionEntries>\n   </BuildAction>\n   <TestAction\n      buildConfiguration = \"Debug\"\n      selectedDebuggerIdentifier = \"Xcode.DebuggerFoundation.Debugger.LLDB\"\n      selectedLauncherIdentifier = \"Xcode.DebuggerFoundation.Launcher.LLDB\"\n      shouldUseLaunchSchemeArgsEnv = \"NO\"\n      enableAddressSanitizer = \"YES\">\n      <Testables>\n         <TestableReference\n            skipped = \"NO\">\n            <BuildableReference\n               BuildableIdentifier = \"primary\"\n               BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n               BuildableName = \"Tests.xctest\"\n               BlueprintName = \"GCDTelnetServer (Tests)\"\n               ReferencedContainer = \"container:GCDTelnetServer.xcodeproj\">\n            </BuildableReference>\n         </TestableReference>\n      </Testables>\n      <MacroExpansion>\n         <BuildableReference\n            BuildableIdentifier = \"primary\"\n            BlueprintIdentifier = \"E298C46B19ED859F00C76821\"\n            BuildableName = \"Tests.xctest\"\n            BlueprintName = \"GCDTelnetServer (Tests)\"\n            ReferencedContainer = \"container:GCDTelnetServer.xcodeproj\">\n         </BuildableReference>\n      </MacroExpansion>\n      <EnvironmentVariables>\n         <EnvironmentVariable\n            key = \"DYLD_INSERT_LIBRARIES\"\n            value = \"/usr/lib/libgmalloc.dylib\"\n            isEnabled = \"YES\">\n         </EnvironmentVariable>\n         <EnvironmentVariable\n            key = \"NSZombieEnabled\"\n            value = \"YES\"\n            isEnabled = \"YES\">\n         </EnvironmentVariable>\n      </EnvironmentVariables>\n      <AdditionalOptions>\n         <AdditionalOption\n            key = \"NSZombieEnabled\"\n            value = \"YES\"\n            isEnabled = \"YES\">\n         </AdditionalOption>\n      </AdditionalOptions>\n   </TestAction>\n   <LaunchAction\n      buildConfiguration = \"Debug\"\n      selectedDebuggerIdentifier = \"Xcode.DebuggerFoundation.Debugger.LLDB\"\n      selectedLauncherIdentifier = \"Xcode.DebuggerFoundation.Launcher.LLDB\"\n      launchStyle = \"0\"\n      useCustomWorkingDirectory = \"NO\"\n      ignoresPersistentStateOnLaunch = \"NO\"\n      debugDocumentVersioning = \"YES\"\n      debugServiceExtension = \"internal\"\n      allowLocationSimulation = \"YES\">\n      <AdditionalOptions>\n      </AdditionalOptions>\n   </LaunchAction>\n   <ProfileAction\n      buildConfiguration = \"Release\"\n      shouldUseLaunchSchemeArgsEnv = \"YES\"\n      savedToolIdentifier = \"\"\n      useCustomWorkingDirectory = \"NO\"\n      debugDocumentVersioning = \"YES\">\n   </ProfileAction>\n   <AnalyzeAction\n      buildConfiguration = \"Release\">\n   </AnalyzeAction>\n   <ArchiveAction\n      buildConfiguration = \"Release\"\n      revealArchiveInOrganizer = \"YES\">\n   </ArchiveAction>\n</Scheme>\n"
  },
  {
    "path": "LICENSE",
    "content": "Copyright (c) 2014, Pierre-Olivier Latour\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n    * Redistributions of source code must retain the above copyright\n      notice, this list of conditions and the following disclaimer.\n    * Redistributions in binary form must reproduce the above copyright\n      notice, this list of conditions and the following disclaimer in the\n      documentation and/or other materials provided with the distribution.\n    * The name of Pierre-Olivier Latour may not be used to endorse\n      or promote products derived from this software without specific\n      prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\nDIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\nON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "README.md",
    "content": "Overview\n========\n\n[![Version](http://cocoapod-badges.herokuapp.com/v/GCDTelnetServer/badge.png)](http://cocoadocs.org/docsets/GCDTelnetServer)\n[![Platform](http://cocoapod-badges.herokuapp.com/p/GCDTelnetServer/badge.png)](https://github.com/swisspol/GCDTelnetServer)\n[![License](http://img.shields.io/cocoapods/l/GCDTelnetServer.svg)](LICENSE)\n\nGCDTelnetServer is a drop-in embedded Telnet server for iOS and OS X apps.\n\nFeatures:\n* Elegant and simple API\n* Fully asynchronous (doesn't need the main thread)\n* Entirely built using [Grand Central Dispatch](http://en.wikipedia.org/wiki/Grand_Central_Dispatch) for best performance and concurrency\n* Support for ANSI colors with an extension on `NSMutableString`\n* Can parse line inputs as command and arguments command line interface\n* Full support for IPv4 and IPv6\n* Automatically handles background and suspended modes on iOS\n* No dependencies on third-party source code\n* Available under a friendly [New BSD License](LICENSE)\n\nRequirements:\n* OS X 10.8 or later (x86_64)\n* iOS 8.0 or later (armv7, armv7s or arm64)\n* ARC memory management only\n\nGetting Started\n===============\n\nDownload or check out the [latest release](https://github.com/swisspol/GCDTelnetServer/releases) of GCDTelnetServer then add both the \"GCDTelnetServer\" and \"GCDNetworking/GCDNetworking\" subfolders to your Xcode project.\n\nAlternatively, you can install GCDTelnetServer using [CocoaPods](http://cocoapods.org/) by simply adding this line to your Xcode project's Podfile:\n```\npod \"GCDTelnetServer\", \"~> 1.0\"\n```\n\nUsing GCDTelnetServer in Your App\n=================================\n\n```objectivec\n#import \"GCDTelnetServer.h\"\n\nGCDTCPServer* server = [[GCDTelnetServer alloc] initWithPort:2323 startHandler:^NSString*(GCDTelnetConnection* connection) {\n  \n  // Return welcome message\n  return [NSString stringWithFormat:@\"You are connected using \\\"%@\\\"\\n\", connection.terminalType];\n  \n} lineHandler:^NSString*(GCDTelnetConnection* connection, NSString* line) {\n  \n  // Simply echo back the received line but you could do anything here\n  return [line stringByAppendingString:@\"\\n\"];\n  \n}];\n[server start];\n```\n\nThen launch Terminal on your Mac, and simply enter `telnet YOUR_COMPUTER_OR_IPHONE_IP_ADDRESS 2323` and voilà, you can communicate \"live\" with your app.\n\n**GCDTelnetServer has an extensive customization API, be sure to peruse [GCDTelnetConnection.h](GCDTelnetServer/GCDTelnetConnection.h).**\n\nExecuting Remote Commands\n=========================\n\nThe most interesting use of GCDTelnetServer is to execute commands inside your app while it's running on the device e.g. to query internal state, trigger actions while the app is in the background, etc...\n\nThis sample code demonstrate how to implement a welcome message with more information (and ANSI colors!), and also support 3 commands (`quit`, `crash` and `setwcolor` which takes some arguments):\n```objectivec\n#import \"GCDTelnetServer.h\"\n#import \"NSMutableString+ANSI.h\"\n\n- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {\n  GCDTCPServer* server = [[GCDTelnetServer alloc] initWithPort:2323 startHandler:^NSString*(GCDTelnetConnection* connection) {\n    \n    UIDevice* device = [UIDevice currentDevice];\n    NSMutableString* welcome = [[NSMutableString alloc] init];\n    [welcome appendANSIStringWithColor:kANSIColor_Green bold:NO format:@\"You are connected from %@ using \\\"%@\\\"\\n\", connection.remoteIPAddress, connection.terminalType];\n    [welcome appendANSIStringWithColor:kANSIColor_Green bold:NO format:@\"Current device is %@ running %@ %@\\n\", device.model, device.systemName, device.systemVersion];\n    return welcome;\n    \n  } commandHandler:^NSString*(GCDTelnetConnection* connection, NSString* command, NSArray* arguments) {\n    \n    if ([command isEqualToString:@\"quit\"]) {\n      [connection close];\n      return nil;\n    } else if ([command isEqualToString:@\"crash\"]) {\n      abort();\n    } else if ([command isEqualToString:@\"setwcolor\"]) {\n      if (arguments.count == 3) {\n        dispatch_async(dispatch_get_main_queue(), ^{\n          _window.backgroundColor = [UIColor colorWithRed:[arguments[0] doubleValue] green:[arguments[1] doubleValue] blue:[arguments[2] doubleValue] alpha:1.0];\n        });\n        return @\"OK\\n\";\n      }\n      return @\"Usage: setwcolor red green blue\\n\";\n    }\n    \n    NSMutableString* error = [[NSMutableString alloc] init];\n    [error appendANSIStringWithColor:kANSIColor_Red bold:YES format:@\"UNKNOWN COMMAND = %@ (%@)\\n\", command, [arguments componentsJoinedByString:@\", \"]];\n    return error;\n    \n  }];\n  [server start];  // TODO: Handle error\n  \n  return YES;\n}\n\n```\n\nAnd here's an example session:\n```sh\n$ telnet localhost 2323\nTrying 127.0.0.1...\nConnected to localhost.\nEscape character is '^]'.\nYou are connected from 127.0.0.1 using \"XTERM-256COLOR\"\nCurrent device is iPad Simulator running iPhone OS 8.1\n> test\nUNKNOWN COMMAND = test ()\n> setwcolor\nUsage: setwcolor red green blue\n> setwcolor 1 0 0\nOK\n> quitConnection closed by foreign host.\n```\n"
  },
  {
    "path": "Run-Tests.sh",
    "content": "#!/bin/bash -ex\n\n# Run GCDNetworking tests first\npushd \"GCDNetworking\"\n./Run-Tests.sh\npopd\n\nOSX_SDK=\"macosx\"\nif [ -z \"$TRAVIS\" ]; then\n  IOS_SDK=\"iphoneos\"\nelse\n  IOS_SDK=\"iphonesimulator\"\nfi\n\nOSX_TARGET=\"GCDTelnetServer (CLT)\"\nIOS_TARGET=\"GCDTelnetServer (iOS)\"\nCONFIGURATION=\"Release\"\n\nBUILD_DIR=\"/tmp/GCDTelnetServer\"\nPRODUCT=\"$BUILD_DIR/$CONFIGURATION/GCDTelnetServer\"\n\n# Build for iOS for oldest deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$IOS_SDK\" -target \"$IOS_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\" \"IPHONEOS_DEPLOYMENT_TARGET=8.0\"\n\n# Build for iOS for default deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$IOS_SDK\" -target \"$IOS_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\"\n\n# Build for OS X for oldest deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$OSX_SDK\" -target \"$OSX_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\" \"MACOSX_DEPLOYMENT_TARGET=10.8\"\n\n# Build for OS X for default deployment target\nrm -rf \"$BUILD_DIR\"\nxcodebuild -sdk \"$OSX_SDK\" -target \"$OSX_TARGET\" -configuration \"$CONFIGURATION\" build \"SYMROOT=$BUILD_DIR\"\n\n# Run tests\nxcodebuild test -scheme \"Tests\"\n\n# Done\necho \"\\nAll tests completed successfully!\"\n"
  },
  {
    "path": "Tests/GCDTelnetServer_Tests.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#pragma clang diagnostic ignored \"-Wgnu-zero-variadic-macro-arguments\"\n#pragma clang diagnostic ignored \"-Wsign-compare\"\n\n#import <XCTest/XCTest.h>\n\n#import \"GCDTelnetServer.h\"\n\n#define kTestPort 3333\n#define kCommunicationSleepDelay (100 * 1000)\n\n@interface GCDTelnetServer_Tests : XCTestCase\n@end\n\n@implementation GCDTelnetServer_Tests\n\n- (void)testCLIParsing {\n  GCDTelnetConnection* connection = [[GCDTelnetConnection alloc] initWithSocket:0];\n  NSArray* array1 = [connection parseLineAsCommandAndArguments:@\"this is 'a test' string \\\"using quoting\\\"\"];\n  NSArray* array2 = @[ @\"this\", @\"is\", @\"a test\", @\"string\", @\"using quoting\" ];\n  XCTAssertEqualObjects(array1, array2);\n}\n\n- (void)testHandlers {\n  GCDTelnetServer* server = [[GCDTelnetServer alloc] initWithPort:kTestPort\n      startHandler:^NSString*(GCDTelnetConnection* connection) {\n        return @\"Hello World!\\n\";\n      }\n      lineHandler:^NSString*(GCDTelnetConnection* connection, NSString* line) {\n        return [line stringByAppendingString:@\"\\n\"];\n      }];\n  XCTAssertTrue([server start]);\n\n  XCTestExpectation* expectation = [self expectationWithDescription:@\"\"];\n  [GCDTCPConnection connectAsynchronouslyToHost:@\"localhost\"\n                                           port:kTestPort\n                                        timeout:1.0\n                                     completion:^(GCDTCPConnection* connection) {\n                                       XCTAssertNotNil(connection);\n                                       [connection open];\n\n                                       usleep(kCommunicationSleepDelay);\n\n                                       NSData* data1 = [connection readDataWithTimeout:1.0];\n                                       XCTAssertEqual(data1.length, 3);\n                                       unsigned char buffer1[] = {255, 253, 3};\n                                       XCTAssertTrue([connection writeData:[NSData dataWithBytes:buffer1 length:sizeof(buffer1)] withTimeout:1.0]);\n\n                                       usleep(kCommunicationSleepDelay);\n\n                                       NSData* data2 = [connection readDataWithTimeout:1.0];\n                                       XCTAssertEqual(data2.length, 3);\n                                       unsigned char buffer2[] = {255, 253, 1};\n                                       XCTAssertTrue([connection writeData:[NSData dataWithBytes:buffer2 length:sizeof(buffer2)] withTimeout:1.0]);\n\n                                       usleep(kCommunicationSleepDelay);\n\n                                       NSData* data3 = [connection readDataWithTimeout:1.0];\n                                       XCTAssertEqual(data3.length, 3);\n                                       unsigned char buffer3[] = {255, 254, 24};\n                                       XCTAssertTrue([connection writeData:[NSData dataWithBytes:buffer3 length:sizeof(buffer3)] withTimeout:1.0]);\n\n                                       usleep(kCommunicationSleepDelay);\n\n                                       NSData* data4 = [connection readDataWithTimeout:1.0];\n                                       XCTAssertNotNil(data4);\n                                       NSString* string4 = [[NSString alloc] initWithData:data4 encoding:NSASCIIStringEncoding];\n                                       XCTAssertEqualObjects(string4, @\"Hello World!\\r\\n> \");\n\n                                       XCTAssertTrue([connection writeString:@\"B\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"o\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"n\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"j\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"o\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"u\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"r\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n                                       XCTAssertTrue([connection writeString:@\"\\r\\0\" withTimeout:1.0]);\n                                       usleep(kCommunicationSleepDelay);\n\n                                       NSData* data5 = [connection readDataWithTimeout:1.0];\n                                       XCTAssertNotNil(data5);\n                                       NSString* string5 = [[NSString alloc] initWithData:data5 encoding:NSASCIIStringEncoding];\n                                       XCTAssertEqualObjects(string5, @\"Bonjour\\r\\nBonjour\\r\\n> \");\n\n                                       [expectation fulfill];\n                                     }];\n  [self waitForExpectationsWithTimeout:10.0 handler:NULL];\n\n  [server stop];\n}\n\n@end\n"
  },
  {
    "path": "iOS/AppDelegate.h",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import <UIKit/UIKit.h>\n\n@interface AppDelegate : UIResponder <UIApplicationDelegate>\n@property(retain, nonatomic) UIWindow* window;\n@end\n"
  },
  {
    "path": "iOS/AppDelegate.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"AppDelegate.h\"\n#import \"GCDTelnetServer.h\"\n#import \"NSMutableString+ANSI.h\"\n\n@implementation AppDelegate\n\n- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions {\n  _window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];\n  _window.backgroundColor = [UIColor whiteColor];\n  _window.rootViewController = [[UIViewController alloc] init];\n  _window.rootViewController.view = [[UIView alloc] init];\n  [_window makeKeyAndVisible];\n\n  GCDTCPServer* server = [[GCDTelnetServer alloc] initWithPort:2323\n      startHandler:^NSString*(GCDTelnetConnection* connection) {\n\n        UIDevice* device = [UIDevice currentDevice];\n        NSMutableString* welcome = [[NSMutableString alloc] init];\n        [welcome appendANSIStringWithColor:kANSIColor_Green bold:NO format:@\"You are connected from %@ using \\\"%@\\\"\\n\", connection.remoteIPAddress, connection.terminalType];\n        [welcome appendANSIStringWithColor:kANSIColor_Green bold:NO format:@\"Current device is %@ running %@ %@\\n\", device.model, device.systemName, device.systemVersion];\n        return welcome;\n\n      }\n      commandHandler:^NSString*(GCDTelnetConnection* connection, NSString* command, NSArray* arguments) {\n\n        if ([command isEqualToString:@\"quit\"]) {\n          [connection close];\n          return nil;\n        } else if ([command isEqualToString:@\"crash\"]) {\n          abort();\n        } else if ([command isEqualToString:@\"setwcolor\"]) {\n          if (arguments.count == 3) {\n            dispatch_async(dispatch_get_main_queue(), ^{\n              _window.backgroundColor = [UIColor colorWithRed:[arguments[0] doubleValue] green:[arguments[1] doubleValue] blue:[arguments[2] doubleValue] alpha:1.0];\n            });\n            return @\"OK\\n\";\n          }\n          return @\"Usage: setwcolor red green blue\\n\";\n        }\n\n        NSMutableString* error = [[NSMutableString alloc] init];\n        [error appendANSIStringWithColor:kANSIColor_Red bold:YES format:@\"UNKNOWN COMMAND = %@ (%@)\\n\", command, [arguments componentsJoinedByString:@\", \"]];\n        return error;\n\n      }];\n  if (![server start]) {\n    abort();\n  }\n  NSLog(@\"Telnet server running on %@\", GCDTCPServerGetPrimaryIPAddress(false));\n\n  return YES;\n}\n\n@end\n"
  },
  {
    "path": "iOS/Info.plist",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">\n<plist version=\"1.0\">\n<dict>\n\t<key>CFBundleDevelopmentRegion</key>\n\t<string>en</string>\n\t<key>CFBundleDisplayName</key>\n\t<string>${PRODUCT_NAME}</string>\n\t<key>CFBundleExecutable</key>\n\t<string>${EXECUTABLE_NAME}</string>\n\t<key>CFBundleIdentifier</key>\n\t<string>net.pol-online.${PRODUCT_NAME:rfc1034identifier}</string>\n\t<key>CFBundleInfoDictionaryVersion</key>\n\t<string>6.0</string>\n\t<key>CFBundleName</key>\n\t<string>${PRODUCT_NAME}</string>\n\t<key>CFBundlePackageType</key>\n\t<string>APPL</string>\n\t<key>CFBundleShortVersionString</key>\n\t<string>1.0</string>\n\t<key>CFBundleVersion</key>\n\t<string>1.0</string>\n\t<key>LSRequiresIPhoneOS</key>\n\t<true/>\n\t<key>UIRequiredDeviceCapabilities</key>\n\t<array>\n\t\t<string>armv7</string>\n\t</array>\n\t<key>UISupportedInterfaceOrientations</key>\n\t<array>\n\t\t<string>UIInterfaceOrientationPortrait</string>\n\t\t<string>UIInterfaceOrientationLandscapeLeft</string>\n\t\t<string>UIInterfaceOrientationLandscapeRight</string>\n\t</array>\n\t<key>UISupportedInterfaceOrientations~ipad</key>\n\t<array>\n\t\t<string>UIInterfaceOrientationPortrait</string>\n\t\t<string>UIInterfaceOrientationPortraitUpsideDown</string>\n\t\t<string>UIInterfaceOrientationLandscapeLeft</string>\n\t\t<string>UIInterfaceOrientationLandscapeRight</string>\n\t</array>\n</dict>\n</plist>\n"
  },
  {
    "path": "iOS/main.m",
    "content": "/*\n Copyright (c) 2014, Pierre-Olivier Latour\n All rights reserved.\n \n Redistribution and use in source and binary forms, with or without\n modification, are permitted provided that the following conditions are met:\n * Redistributions of source code must retain the above copyright\n notice, this list of conditions and the following disclaimer.\n * Redistributions in binary form must reproduce the above copyright\n notice, this list of conditions and the following disclaimer in the\n documentation and/or other materials provided with the distribution.\n * The name of Pierre-Olivier Latour may not be used to endorse\n or promote products derived from this software without specific\n prior written permission.\n \n THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\n ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\n WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\n DISCLAIMED. IN NO EVENT SHALL PIERRE-OLIVIER LATOUR BE LIABLE FOR ANY\n DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\n ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n */\n\n#import \"AppDelegate.h\"\n\nint main(int argc, char* argv[]) {\n  @autoreleasepool {\n    return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));\n  }\n}\n"
  }
]