├── Brokenithm-iOS ├── zh.lproj │ ├── Main.strings │ └── Localizable.strings ├── Settings.bundle │ ├── en.lproj │ │ └── Root.strings │ ├── zh.lproj │ │ └── Root.strings │ └── Root.plist ├── Assets.xcassets │ ├── Contents.json │ └── AppIcon.appiconset │ │ ├── Icon.png │ │ ├── icon_20pt.png │ │ ├── icon_29pt.png │ │ ├── icon_40pt.png │ │ ├── icon_76pt.png │ │ ├── icon_20pt@2x.png │ │ ├── icon_20pt@3x.png │ │ ├── icon_29pt@2x.png │ │ ├── icon_29pt@3x.png │ │ ├── icon_40pt@2x.png │ │ ├── icon_40pt@3x.png │ │ ├── icon_60pt@2x.png │ │ ├── icon_60pt@3x.png │ │ ├── icon_76pt@2x.png │ │ ├── icon_83.5@2x.png │ │ ├── icon_20pt@2x-1.png │ │ ├── icon_29pt@2x-1.png │ │ ├── icon_40pt@2x-1.png │ │ └── Contents.json ├── MainApp.h ├── FunctionButton.h ├── AppDelegate.h ├── main.m ├── MainApp.m ├── SocketDelegate.h ├── FunctionButton.m ├── ViewController.h ├── Info.plist ├── Base.lproj │ └── Main.storyboard ├── AppDelegate.m ├── SocketDelegate.m └── ViewController.m ├── Gemfile ├── Pods ├── Headers │ ├── Private │ │ └── CocoaAsyncSocket │ │ │ ├── GCDAsyncSocket.h │ │ │ └── GCDAsyncUdpSocket.h │ └── Public │ │ └── CocoaAsyncSocket │ │ ├── GCDAsyncSocket.h │ │ └── GCDAsyncUdpSocket.h ├── Target Support Files │ ├── CocoaAsyncSocket │ │ ├── CocoaAsyncSocket-dummy.m │ │ ├── CocoaAsyncSocket-prefix.pch │ │ ├── CocoaAsyncSocket.debug.xcconfig │ │ ├── CocoaAsyncSocket.release.xcconfig │ │ └── CocoaAsyncSocket.xcconfig │ └── Pods-Brokenithm-iOS │ │ ├── Pods-Brokenithm-iOS-dummy.m │ │ ├── Pods-Brokenithm-iOS-acknowledgements.markdown │ │ ├── Pods-Brokenithm-iOS.debug.xcconfig │ │ ├── Pods-Brokenithm-iOS.release.xcconfig │ │ ├── Pods-Brokenithm-iOS-acknowledgements.plist │ │ ├── Pods-Brokenithm-iOS-resources.sh │ │ └── Pods-Brokenithm-iOS-frameworks.sh ├── Manifest.lock ├── CocoaAsyncSocket │ ├── LICENSE.txt │ ├── README.markdown │ └── Source │ │ └── GCD │ │ └── GCDAsyncUdpSocket.h └── Pods.xcodeproj │ └── project.pbxproj ├── Brokenithm-iOS.xcodeproj ├── project.xcworkspace │ ├── contents.xcworkspacedata │ └── xcshareddata │ │ └── IDEWorkspaceChecks.plist ├── xcuserdata │ └── ester.xcuserdatad │ │ └── xcschemes │ │ └── xcschememanagement.plist ├── xcshareddata │ └── xcschemes │ │ ├── Brokenithm-iOS.xcscheme │ │ └── Brokenithm-iOS-Release.xcscheme └── project.pbxproj ├── Brokenithm-iOS.xcworkspace ├── contents.xcworkspacedata └── xcshareddata │ └── IDEWorkspaceChecks.plist ├── Podfile ├── fastlane ├── Appfile ├── README.md └── Fastfile ├── Podfile.lock ├── README.md ├── .gitignore └── Gemfile.lock /Brokenithm-iOS/zh.lproj/Main.strings: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Brokenithm-iOS/Settings.bundle/en.lproj/Root.strings: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /Gemfile: -------------------------------------------------------------------------------- 1 | source "https://rubygems.org" 2 | 3 | gem "fastlane" 4 | -------------------------------------------------------------------------------- /Pods/Headers/Private/CocoaAsyncSocket/GCDAsyncSocket.h: -------------------------------------------------------------------------------- 1 | ../../../CocoaAsyncSocket/Source/GCD/GCDAsyncSocket.h -------------------------------------------------------------------------------- /Pods/Headers/Public/CocoaAsyncSocket/GCDAsyncSocket.h: -------------------------------------------------------------------------------- 1 | ../../../CocoaAsyncSocket/Source/GCD/GCDAsyncSocket.h -------------------------------------------------------------------------------- /Pods/Headers/Private/CocoaAsyncSocket/GCDAsyncUdpSocket.h: -------------------------------------------------------------------------------- 1 | ../../../CocoaAsyncSocket/Source/GCD/GCDAsyncUdpSocket.h -------------------------------------------------------------------------------- /Pods/Headers/Public/CocoaAsyncSocket/GCDAsyncUdpSocket.h: -------------------------------------------------------------------------------- 1 | ../../../CocoaAsyncSocket/Source/GCD/GCDAsyncUdpSocket.h -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /Brokenithm-iOS/Settings.bundle/zh.lproj/Root.strings: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Settings.bundle/zh.lproj/Root.strings -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/Icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/Icon.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_76pt.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_76pt.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@3x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@3x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@3x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_60pt@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_60pt@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_60pt@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_60pt@3x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_76pt@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_76pt@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_83.5@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_83.5@2x.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@2x-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_20pt@2x-1.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@2x-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_29pt@2x-1.png -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@2x-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/esterTion/Brokenithm-iOS/HEAD/Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/icon_40pt@2x-1.png -------------------------------------------------------------------------------- /Pods/Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_CocoaAsyncSocket : NSObject 3 | @end 4 | @implementation PodsDummy_CocoaAsyncSocket 5 | @end 6 | -------------------------------------------------------------------------------- /Brokenithm-iOS/zh.lproj/Localizable.strings: -------------------------------------------------------------------------------- 1 | { 2 | "Not connected" = "未连接"; 3 | "Connected" = "已连接"; 4 | "Enable Air Input" = "启用Air输入"; 5 | "Insert Coin" = "投币"; 6 | "Read Card" = "刷卡"; 7 | "More..." = "更多设置…"; 8 | } 9 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS-dummy.m: -------------------------------------------------------------------------------- 1 | #import 2 | @interface PodsDummy_Pods_Brokenithm_iOS : NSObject 3 | @end 4 | @implementation PodsDummy_Pods_Brokenithm_iOS 5 | @end 6 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /Pods/Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket-prefix.pch: -------------------------------------------------------------------------------- 1 | #ifdef __OBJC__ 2 | #import 3 | #else 4 | #ifndef FOUNDATION_EXPORT 5 | #if defined(__cplusplus) 6 | #define FOUNDATION_EXPORT extern "C" 7 | #else 8 | #define FOUNDATION_EXPORT extern 9 | #endif 10 | #endif 11 | #endif 12 | 13 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /Podfile: -------------------------------------------------------------------------------- 1 | # Uncomment the next line to define a global platform for your project 2 | platform :ios, '8.0' 3 | 4 | target 'Brokenithm-iOS' do 5 | # Uncomment the next line if you're using Swift or would like to use dynamic frameworks 6 | # use_frameworks! 7 | 8 | # Pods for Brokenithm-iOS 9 | pod 'CocoaAsyncSocket' 10 | 11 | end 12 | -------------------------------------------------------------------------------- /Brokenithm-iOS/MainApp.h: -------------------------------------------------------------------------------- 1 | // 2 | // MainApp.h 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/3/2. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #pragma once 10 | 11 | #import 12 | #import "ViewController.h" 13 | 14 | @interface MainApp : UIApplication 15 | @property ViewController *vc; 16 | @end 17 | -------------------------------------------------------------------------------- /Brokenithm-iOS/FunctionButton.h: -------------------------------------------------------------------------------- 1 | // 2 | // FunctionButton.h 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/3/4. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #pragma once 10 | 11 | #import 12 | 13 | @interface FunctionButton : UILabel 14 | @property NSString *name; 15 | -(id)initAtY:(CGFloat)y; 16 | @end 17 | -------------------------------------------------------------------------------- /Brokenithm-iOS/AppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.h 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/28. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface AppDelegate : UIResponder 12 | 13 | @property (strong, nonatomic) UIWindow *window; 14 | 15 | 16 | @end 17 | 18 | -------------------------------------------------------------------------------- /fastlane/Appfile: -------------------------------------------------------------------------------- 1 | app_identifier("com.estertion.brokenithm-ios") # The bundle identifier of your app 2 | apple_id("superk589@gmail.com") # Your Apple email address 3 | 4 | itc_team_id("118308934") # App Store Connect Team ID 5 | team_id("MXJJEEMF3U") # Developer Portal Team ID 6 | 7 | # For more information about the Appfile, see: 8 | # https://docs.fastlane.tools/advanced/#appfile 9 | -------------------------------------------------------------------------------- /Podfile.lock: -------------------------------------------------------------------------------- 1 | PODS: 2 | - CocoaAsyncSocket (7.6.3) 3 | 4 | DEPENDENCIES: 5 | - CocoaAsyncSocket 6 | 7 | SPEC REPOS: 8 | https://github.com/CocoaPods/Specs.git: 9 | - CocoaAsyncSocket 10 | 11 | SPEC CHECKSUMS: 12 | CocoaAsyncSocket: eafaa68a7e0ec99ead0a7b35015e0bf25d2c8987 13 | 14 | PODFILE CHECKSUM: 203779727e696b4a59a26ea541d7cfcfdf196b38 15 | 16 | COCOAPODS: 1.9.0 17 | -------------------------------------------------------------------------------- /Pods/Manifest.lock: -------------------------------------------------------------------------------- 1 | PODS: 2 | - CocoaAsyncSocket (7.6.3) 3 | 4 | DEPENDENCIES: 5 | - CocoaAsyncSocket 6 | 7 | SPEC REPOS: 8 | https://github.com/CocoaPods/Specs.git: 9 | - CocoaAsyncSocket 10 | 11 | SPEC CHECKSUMS: 12 | CocoaAsyncSocket: eafaa68a7e0ec99ead0a7b35015e0bf25d2c8987 13 | 14 | PODFILE CHECKSUM: 203779727e696b4a59a26ea541d7cfcfdf196b38 15 | 16 | COCOAPODS: 1.9.0 17 | -------------------------------------------------------------------------------- /Brokenithm-iOS/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/28. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "AppDelegate.h" 11 | 12 | int main(int argc, char * argv[]) { 13 | @autoreleasepool { 14 | return UIApplicationMain(argc, argv, @"MainApp", NSStringFromClass([AppDelegate class])); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## Brokenithm-iOS 2 | 3 | A version of Brokenithm, based on Brokenithm-Evolved, based on Brokenithm. 4 | Using usbmux to communicate over USB, rather than wifi to prevent sudden lag. 5 | 6 | ### Branches 7 | `master` branch is iOS App branch, the controller itself. 8 | `win-client-cpp_(failed)` branch is initial client branch written in C++, and abandoned due to library too old. 9 | `win-client` branch is current client branch written in C#. 10 | 11 | ### Build env 12 | - Xcode 11.3.1 13 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS-acknowledgements.markdown: -------------------------------------------------------------------------------- 1 | # Acknowledgements 2 | This application makes use of the following third party libraries: 3 | 4 | ## CocoaAsyncSocket 5 | 6 | Public Domain License 7 | 8 | The CocoaAsyncSocket project is in the public domain. 9 | 10 | The original TCP version (AsyncSocket) was created by Dustin Voss in January 2003. 11 | Updated and maintained by Deusty LLC and the Apple development community. 12 | 13 | Generated by CocoaPods - https://cocoapods.org 14 | -------------------------------------------------------------------------------- /Brokenithm-iOS/MainApp.m: -------------------------------------------------------------------------------- 1 | // 2 | // MainApp.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/3/2. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import 10 | #import "MainApp.h" 11 | 12 | @interface MainApp () 13 | @end 14 | 15 | @implementation MainApp 16 | 17 | -(void)sendEvent:(UIEvent *)event { 18 | [super sendEvent:event]; 19 | if (event.type == UIEventTypeTouches) { 20 | [(ViewController*)self.keyWindow.rootViewController updateTouches:event]; 21 | } 22 | } 23 | 24 | @end 25 | -------------------------------------------------------------------------------- /Brokenithm-iOS/SocketDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // SocketDelegate.h 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/29. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #ifndef SocketDelegate_h 10 | #define SocketDelegate_h 11 | 12 | @class ViewController; 13 | 14 | #import 15 | #import 16 | #import "ViewController.h" 17 | 18 | @interface SocketDelegate : NSObject { 19 | GCDAsyncSocket *server; 20 | NSMutableArray *connectedSockets; 21 | } 22 | @property ViewController *parentVc; 23 | 24 | - (void)BroadcastData:(NSData*)data; 25 | 26 | @end 27 | 28 | #endif /* SocketDelegate_h */ 29 | -------------------------------------------------------------------------------- /Brokenithm-iOS/FunctionButton.m: -------------------------------------------------------------------------------- 1 | // 2 | // FunctionButton.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/3/4. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import "FunctionButton.h" 10 | 11 | @implementation FunctionButton 12 | 13 | -(id)initAtY:(CGFloat)y { 14 | self = [super initWithFrame:CGRectMake(0, y, 200, 60)]; 15 | self.textAlignment = NSTextAlignmentCenter; 16 | self.textColor = [UIColor whiteColor]; 17 | self.numberOfLines = 1; 18 | self.backgroundColor = [UIColor blackColor]; 19 | self.layer.borderColor = [UIColor whiteColor].CGColor; 20 | self.layer.borderWidth = 1.0; 21 | return self; 22 | } 23 | 24 | @end 25 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS.debug.xcconfig: -------------------------------------------------------------------------------- 1 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 2 | HEADER_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/CocoaAsyncSocket" 3 | LIBRARY_SEARCH_PATHS = $(inherited) "${PODS_CONFIGURATION_BUILD_DIR}/CocoaAsyncSocket" 4 | OTHER_LDFLAGS = $(inherited) -ObjC -l"CocoaAsyncSocket" -framework "CFNetwork" -framework "Security" 5 | PODS_BUILD_DIR = ${BUILD_DIR} 6 | PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 7 | PODS_PODFILE_DIR_PATH = ${SRCROOT}/. 8 | PODS_ROOT = ${SRCROOT}/Pods 9 | USE_RECURSIVE_SCRIPT_INPUTS_IN_SCRIPT_PHASES = YES 10 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS.release.xcconfig: -------------------------------------------------------------------------------- 1 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 2 | HEADER_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/CocoaAsyncSocket" 3 | LIBRARY_SEARCH_PATHS = $(inherited) "${PODS_CONFIGURATION_BUILD_DIR}/CocoaAsyncSocket" 4 | OTHER_LDFLAGS = $(inherited) -ObjC -l"CocoaAsyncSocket" -framework "CFNetwork" -framework "Security" 5 | PODS_BUILD_DIR = ${BUILD_DIR} 6 | PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 7 | PODS_PODFILE_DIR_PATH = ${SRCROOT}/. 8 | PODS_ROOT = ${SRCROOT}/Pods 9 | USE_RECURSIVE_SCRIPT_INPUTS_IN_SCRIPT_PHASES = YES 10 | -------------------------------------------------------------------------------- /Pods/Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket.debug.xcconfig: -------------------------------------------------------------------------------- 1 | CONFIGURATION_BUILD_DIR = ${PODS_CONFIGURATION_BUILD_DIR}/CocoaAsyncSocket 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Headers/Private" "${PODS_ROOT}/Headers/Private/CocoaAsyncSocket" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/CocoaAsyncSocket" 4 | PODS_BUILD_DIR = ${BUILD_DIR} 5 | PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 6 | PODS_ROOT = ${SRCROOT} 7 | PODS_TARGET_SRCROOT = ${PODS_ROOT}/CocoaAsyncSocket 8 | PRODUCT_BUNDLE_IDENTIFIER = org.cocoapods.${PRODUCT_NAME:rfc1034identifier} 9 | SKIP_INSTALL = YES 10 | USE_RECURSIVE_SCRIPT_INPUTS_IN_SCRIPT_PHASES = YES 11 | -------------------------------------------------------------------------------- /Pods/Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket.release.xcconfig: -------------------------------------------------------------------------------- 1 | CONFIGURATION_BUILD_DIR = ${PODS_CONFIGURATION_BUILD_DIR}/CocoaAsyncSocket 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Headers/Private" "${PODS_ROOT}/Headers/Private/CocoaAsyncSocket" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/CocoaAsyncSocket" 4 | PODS_BUILD_DIR = ${BUILD_DIR} 5 | PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 6 | PODS_ROOT = ${SRCROOT} 7 | PODS_TARGET_SRCROOT = ${PODS_ROOT}/CocoaAsyncSocket 8 | PRODUCT_BUNDLE_IDENTIFIER = org.cocoapods.${PRODUCT_NAME:rfc1034identifier} 9 | SKIP_INSTALL = YES 10 | USE_RECURSIVE_SCRIPT_INPUTS_IN_SCRIPT_PHASES = YES 11 | -------------------------------------------------------------------------------- /Pods/Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket.xcconfig: -------------------------------------------------------------------------------- 1 | CONFIGURATION_BUILD_DIR = ${PODS_CONFIGURATION_BUILD_DIR}/CocoaAsyncSocket 2 | GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1 3 | HEADER_SEARCH_PATHS = $(inherited) "${PODS_ROOT}/Headers/Private" "${PODS_ROOT}/Headers/Private/CocoaAsyncSocket" "${PODS_ROOT}/Headers/Public" "${PODS_ROOT}/Headers/Public/CocoaAsyncSocket" 4 | OTHER_LDFLAGS = -framework "CFNetwork" -framework "Security" 5 | PODS_BUILD_DIR = ${BUILD_DIR} 6 | PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME) 7 | PODS_ROOT = ${SRCROOT} 8 | PODS_TARGET_SRCROOT = ${PODS_ROOT}/CocoaAsyncSocket 9 | PRODUCT_BUNDLE_IDENTIFIER = org.cocoapods.${PRODUCT_NAME:rfc1034identifier} 10 | SKIP_INSTALL = YES 11 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/xcuserdata/ester.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | Brokenithm-iOS-Release.xcscheme_^#shared#^_ 8 | 9 | orderHint 10 | 3 11 | 12 | Brokenithm-iOS.xcscheme_^#shared#^_ 13 | 14 | orderHint 15 | 0 16 | 17 | 18 | SuppressBuildableAutocreation 19 | 20 | 1968E72024086C2100784829 21 | 22 | primary 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /fastlane/README.md: -------------------------------------------------------------------------------- 1 | fastlane documentation 2 | ================ 3 | # Installation 4 | 5 | Make sure you have the latest version of the Xcode command line tools installed: 6 | 7 | ``` 8 | xcode-select --install 9 | ``` 10 | 11 | Install _fastlane_ using 12 | ``` 13 | [sudo] gem install fastlane -NV 14 | ``` 15 | or alternatively using `brew cask install fastlane` 16 | 17 | # Available Actions 18 | ## iOS 19 | ### ios beta 20 | ``` 21 | fastlane ios beta 22 | ``` 23 | Push a new beta build to TestFlight 24 | 25 | ---- 26 | 27 | This README.md is auto-generated and will be re-generated every time [fastlane](https://fastlane.tools) is run. 28 | More information about fastlane can be found on [fastlane.tools](https://fastlane.tools). 29 | The documentation of fastlane can be found on [docs.fastlane.tools](https://docs.fastlane.tools). 30 | -------------------------------------------------------------------------------- /fastlane/Fastfile: -------------------------------------------------------------------------------- 1 | # This file contains the fastlane.tools configuration 2 | # You can find the documentation at https://docs.fastlane.tools 3 | # 4 | # For a list of all available actions, check out 5 | # 6 | # https://docs.fastlane.tools/actions 7 | # 8 | # For a list of all available plugins, check out 9 | # 10 | # https://docs.fastlane.tools/plugins/available-plugins 11 | # 12 | 13 | # Uncomment the line if you want fastlane to automatically update itself 14 | # update_fastlane 15 | 16 | default_platform(:ios) 17 | 18 | platform :ios do 19 | desc "Push a new beta build to TestFlight" 20 | lane :beta do 21 | increment_build_number( 22 | build_number: latest_testflight_build_number + 1, 23 | xcodeproj: "Brokenithm-iOS.xcodeproj" 24 | ) 25 | build_app(workspace: "Brokenithm-iOS.xcworkspace", scheme: "Brokenithm-iOS") 26 | upload_to_testflight 27 | end 28 | end 29 | -------------------------------------------------------------------------------- /Brokenithm-iOS/ViewController.h: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.h 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/28. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #pragma once 10 | 11 | @class SocketDelegate; 12 | @class MainView; 13 | 14 | #import 15 | #import 16 | #import "SocketDelegate.h" 17 | #import "MainApp.h" 18 | 19 | @interface ViewController : UIViewController { 20 | float screenWidth; 21 | float screenHeight; 22 | SocketDelegate *server; 23 | UILabel *connectStatusView; 24 | CAGradientLayer *ledBackground; 25 | 26 | BOOL openCloseEventOnce; 27 | BOOL funcViewOn; 28 | UIView *functionBtnView; 29 | UILabel *openCloseBtn; 30 | UISwitch *enableAirToggle; 31 | BOOL airEnabled; 32 | BOOL autoPopMenu; 33 | BOOL invertAir; 34 | NSNumber *menuHoldDuration; 35 | UILongPressGestureRecognizer *openCloseHold; 36 | int touchCount; 37 | } 38 | @property UIView *airIOView; 39 | @property UIView *sliderIOView; 40 | 41 | -(void)updateLed:(NSData*)rgbData; 42 | -(void)updateTouches:(UIEvent *)event; 43 | -(void)connected; 44 | -(void)disconnected; 45 | -(void)becomeInactive; 46 | -(void)becomeActive; 47 | 48 | @end 49 | 50 | struct ioBuf { 51 | uint8_t len; 52 | char head[3]; 53 | uint8_t air[6]; 54 | uint8_t slider[32]; 55 | uint8_t testBtn; 56 | uint8_t serviceBtn; 57 | }; 58 | 59 | enum { 60 | BNI_FUNCTION_COIN = 1, 61 | BNI_FUNCTION_CARD 62 | }; 63 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS-acknowledgements.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | PreferenceSpecifiers 6 | 7 | 8 | FooterText 9 | This application makes use of the following third party libraries: 10 | Title 11 | Acknowledgements 12 | Type 13 | PSGroupSpecifier 14 | 15 | 16 | FooterText 17 | Public Domain License 18 | 19 | The CocoaAsyncSocket project is in the public domain. 20 | 21 | The original TCP version (AsyncSocket) was created by Dustin Voss in January 2003. 22 | Updated and maintained by Deusty LLC and the Apple development community. 23 | 24 | License 25 | public domain 26 | Title 27 | CocoaAsyncSocket 28 | Type 29 | PSGroupSpecifier 30 | 31 | 32 | FooterText 33 | Generated by CocoaPods - https://cocoapods.org 34 | Title 35 | 36 | Type 37 | PSGroupSpecifier 38 | 39 | 40 | StringsTable 41 | Acknowledgements 42 | Title 43 | Acknowledgements 44 | 45 | 46 | -------------------------------------------------------------------------------- /Brokenithm-iOS/Settings.bundle/Root.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | StringsTable 6 | Root 7 | PreferenceSpecifiers 8 | 9 | 10 | Type 11 | PSToggleSwitchSpecifier 12 | Title 13 | Enable Air Input 14 | Key 15 | enableAir 16 | DefaultValue 17 | 18 | 19 | 20 | Type 21 | PSToggleSwitchSpecifier 22 | Title 23 | Auto Pop Menu 24 | Key 25 | autoPopMenu 26 | DefaultValue 27 | 28 | 29 | 30 | Type 31 | PSToggleSwitchSpecifier 32 | Title 33 | Invert Air Input Layout 34 | Key 35 | invertAir 36 | DefaultValue 37 | 38 | 39 | 40 | Type 41 | PSTitleValueSpecifier 42 | DefaultValue 43 | 44 | Title 45 | Hold duration to open side menu 46 | Key 47 | menuDurationTitle 48 | 49 | 50 | Type 51 | PSSliderSpecifier 52 | Key 53 | menuDuration 54 | MinimumValue 55 | 0.5 56 | DefaultValue 57 | 1 58 | MaximumValue 59 | 2 60 | 61 | 62 | 63 | 64 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Xcode 2 | # 3 | # gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore 4 | 5 | ## User settings 6 | xcuserdata/ 7 | 8 | ## compatibility with Xcode 8 and earlier (ignoring not required starting Xcode 9) 9 | *.xcscmblueprint 10 | *.xccheckout 11 | 12 | ## compatibility with Xcode 3 and earlier (ignoring not required starting Xcode 4) 13 | build/ 14 | DerivedData/ 15 | *.moved-aside 16 | *.pbxuser 17 | !default.pbxuser 18 | *.mode1v3 19 | !default.mode1v3 20 | *.mode2v3 21 | !default.mode2v3 22 | *.perspectivev3 23 | !default.perspectivev3 24 | 25 | ## Obj-C/Swift specific 26 | *.hmap 27 | 28 | ## App packaging 29 | *.ipa 30 | *.dSYM.zip 31 | *.dSYM 32 | 33 | # CocoaPods 34 | # 35 | # We recommend against adding the Pods directory to your .gitignore. However 36 | # you should judge for yourself, the pros and cons are mentioned at: 37 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control 38 | # 39 | # Pods/ 40 | # 41 | # Add this line if you want to avoid checking in source code from the Xcode workspace 42 | # *.xcworkspace 43 | 44 | # Carthage 45 | # 46 | # Add this line if you want to avoid checking in source code from Carthage dependencies. 47 | # Carthage/Checkouts 48 | 49 | Carthage/Build/ 50 | 51 | # fastlane 52 | # 53 | # It is recommended to not store the screenshots in the git repo. 54 | # Instead, use fastlane to re-generate the screenshots whenever they are needed. 55 | # For more information about the recommended setup visit: 56 | # https://docs.fastlane.tools/best-practices/source-control/#source-control 57 | 58 | fastlane/report.xml 59 | fastlane/Preview.html 60 | fastlane/screenshots/**/*.png 61 | fastlane/test_output 62 | 63 | # Code Injection 64 | # 65 | # After new code Injection tools there's a generated folder /iOSInjectionProject 66 | # https://github.com/johnno1962/injectionforxcode 67 | 68 | iOSInjectionProject/ 69 | .DS_Store 70 | -------------------------------------------------------------------------------- /Brokenithm-iOS/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleDisplayName 8 | Brokenithm-iOS 9 | CFBundleExecutable 10 | $(EXECUTABLE_NAME) 11 | CFBundleIdentifier 12 | $(PRODUCT_BUNDLE_IDENTIFIER) 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleLocalizations 16 | 17 | en 18 | zh 19 | 20 | CFBundleName 21 | $(PRODUCT_NAME) 22 | CFBundlePackageType 23 | APPL 24 | CFBundleShortVersionString 25 | $(MARKETING_VERSION) 26 | CFBundleVersion 27 | $(CURRENT_PROJECT_VERSION) 28 | LSRequiresIPhoneOS 29 | 30 | UILaunchStoryboardName 31 | Main 32 | UIMainStoryboardFile 33 | Main 34 | UIRequiredDeviceCapabilities 35 | 36 | armv7 37 | 38 | UIRequiresFullScreen 39 | 40 | UIStatusBarHidden 41 | 42 | UIStatusBarStyle 43 | UIStatusBarStyleLightContent 44 | UISupportedInterfaceOrientations 45 | 46 | UIInterfaceOrientationLandscapeLeft 47 | UIInterfaceOrientationLandscapeRight 48 | 49 | UISupportedInterfaceOrientations~ipad 50 | 51 | UIInterfaceOrientationLandscapeLeft 52 | UIInterfaceOrientationLandscapeRight 53 | 54 | UIViewControllerBasedStatusBarAppearance 55 | 56 | 57 | 58 | -------------------------------------------------------------------------------- /Pods/CocoaAsyncSocket/LICENSE.txt: -------------------------------------------------------------------------------- 1 | This library is in the public domain. 2 | However, not all organizations are allowed to use such a license. 3 | For example, Germany doesn't recognize the Public Domain and one is not allowed to use libraries under such license (or similar). 4 | 5 | Thus, the library is now dual licensed, 6 | and one is allowed to choose which license they would like to use. 7 | 8 | ################################################## 9 | License Option #1 : 10 | ################################################## 11 | 12 | Public Domain 13 | 14 | ################################################## 15 | License Option #2 : 16 | ################################################## 17 | 18 | Software License Agreement (BSD License) 19 | 20 | Copyright (c) 2017, Deusty, LLC 21 | All rights reserved. 22 | 23 | Redistribution and use of this software in source and binary forms, 24 | with or without modification, are permitted provided that the following conditions are met: 25 | 26 | * Redistributions of source code must retain the above 27 | copyright notice, this list of conditions and the 28 | following disclaimer. 29 | 30 | * Neither the name of Deusty LLC nor the names of its 31 | contributors may be used to endorse or promote products 32 | derived from this software without specific prior 33 | written permission of Deusty LLC. 34 | 35 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -------------------------------------------------------------------------------- /Brokenithm-iOS/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | -------------------------------------------------------------------------------- /Brokenithm-iOS/AppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/28. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import "AppDelegate.h" 10 | 11 | @interface AppDelegate () 12 | 13 | @end 14 | 15 | @implementation AppDelegate 16 | 17 | 18 | - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { 19 | // Override point for customization after application launch. 20 | return YES; 21 | } 22 | 23 | 24 | - (void)applicationWillResignActive:(UIApplication *)application { 25 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 26 | // Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game. 27 | } 28 | 29 | 30 | - (void)applicationDidEnterBackground:(UIApplication *)application { 31 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 32 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 33 | } 34 | 35 | 36 | - (void)applicationWillEnterForeground:(UIApplication *)application { 37 | // Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background. 38 | } 39 | 40 | 41 | - (void)applicationDidBecomeActive:(UIApplication *)application { 42 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 43 | } 44 | 45 | 46 | - (void)applicationWillTerminate:(UIApplication *)application { 47 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 48 | } 49 | 50 | 51 | @end 52 | -------------------------------------------------------------------------------- /Brokenithm-iOS/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "size" : "20x20", 5 | "idiom" : "iphone", 6 | "filename" : "icon_20pt@2x.png", 7 | "scale" : "2x" 8 | }, 9 | { 10 | "size" : "20x20", 11 | "idiom" : "iphone", 12 | "filename" : "icon_20pt@3x.png", 13 | "scale" : "3x" 14 | }, 15 | { 16 | "size" : "29x29", 17 | "idiom" : "iphone", 18 | "filename" : "icon_29pt@2x.png", 19 | "scale" : "2x" 20 | }, 21 | { 22 | "size" : "29x29", 23 | "idiom" : "iphone", 24 | "filename" : "icon_29pt@3x.png", 25 | "scale" : "3x" 26 | }, 27 | { 28 | "size" : "40x40", 29 | "idiom" : "iphone", 30 | "filename" : "icon_40pt@2x.png", 31 | "scale" : "2x" 32 | }, 33 | { 34 | "size" : "40x40", 35 | "idiom" : "iphone", 36 | "filename" : "icon_40pt@3x.png", 37 | "scale" : "3x" 38 | }, 39 | { 40 | "size" : "60x60", 41 | "idiom" : "iphone", 42 | "filename" : "icon_60pt@2x.png", 43 | "scale" : "2x" 44 | }, 45 | { 46 | "size" : "60x60", 47 | "idiom" : "iphone", 48 | "filename" : "icon_60pt@3x.png", 49 | "scale" : "3x" 50 | }, 51 | { 52 | "size" : "20x20", 53 | "idiom" : "ipad", 54 | "filename" : "icon_20pt.png", 55 | "scale" : "1x" 56 | }, 57 | { 58 | "size" : "20x20", 59 | "idiom" : "ipad", 60 | "filename" : "icon_20pt@2x-1.png", 61 | "scale" : "2x" 62 | }, 63 | { 64 | "size" : "29x29", 65 | "idiom" : "ipad", 66 | "filename" : "icon_29pt.png", 67 | "scale" : "1x" 68 | }, 69 | { 70 | "size" : "29x29", 71 | "idiom" : "ipad", 72 | "filename" : "icon_29pt@2x-1.png", 73 | "scale" : "2x" 74 | }, 75 | { 76 | "size" : "40x40", 77 | "idiom" : "ipad", 78 | "filename" : "icon_40pt.png", 79 | "scale" : "1x" 80 | }, 81 | { 82 | "size" : "40x40", 83 | "idiom" : "ipad", 84 | "filename" : "icon_40pt@2x-1.png", 85 | "scale" : "2x" 86 | }, 87 | { 88 | "size" : "76x76", 89 | "idiom" : "ipad", 90 | "filename" : "icon_76pt.png", 91 | "scale" : "1x" 92 | }, 93 | { 94 | "size" : "76x76", 95 | "idiom" : "ipad", 96 | "filename" : "icon_76pt@2x.png", 97 | "scale" : "2x" 98 | }, 99 | { 100 | "size" : "83.5x83.5", 101 | "idiom" : "ipad", 102 | "filename" : "icon_83.5@2x.png", 103 | "scale" : "2x" 104 | }, 105 | { 106 | "size" : "1024x1024", 107 | "idiom" : "ios-marketing", 108 | "filename" : "Icon.png", 109 | "scale" : "1x" 110 | } 111 | ], 112 | "info" : { 113 | "version" : 1, 114 | "author" : "xcode" 115 | } 116 | } -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/xcshareddata/xcschemes/Brokenithm-iOS.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 37 | 38 | 39 | 40 | 41 | 42 | 52 | 54 | 60 | 61 | 62 | 63 | 69 | 71 | 77 | 78 | 79 | 80 | 82 | 83 | 86 | 87 | 88 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/xcshareddata/xcschemes/Brokenithm-iOS-Release.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 11 | 15 | 16 | 17 | 18 | 19 | 25 | 31 | 32 | 33 | 34 | 35 | 40 | 41 | 42 | 43 | 53 | 55 | 61 | 62 | 63 | 64 | 70 | 71 | 77 | 78 | 79 | 80 | 82 | 83 | 86 | 87 | 88 | -------------------------------------------------------------------------------- /Brokenithm-iOS/SocketDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // SocketDelegate.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/29. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import "SocketDelegate.h" 10 | 11 | @interface SocketDelegate () 12 | @end 13 | 14 | @implementation SocketDelegate 15 | 16 | - (id)init { 17 | server = [[GCDAsyncSocket alloc] initWithDelegate:(id)self delegateQueue:dispatch_get_main_queue()]; 18 | [self acceptConnection]; 19 | connectedSockets = [[NSMutableArray alloc] initWithCapacity:1]; 20 | [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(becomeInactive) name:UIApplicationWillResignActiveNotification object:nil]; 21 | [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(becomeActive) name:UIApplicationDidBecomeActiveNotification object:nil]; 22 | return [super init]; 23 | } 24 | - (void)acceptConnection { 25 | NSError *error = nil; 26 | if (![server acceptOnPort:24864 error:&error]) { 27 | NSLog(@"error creating server: %@", error); 28 | } 29 | } 30 | 31 | - (void)socket:(GCDAsyncSocket *)sock didAcceptNewSocket:(GCDAsyncSocket *)newSocket { 32 | @synchronized(connectedSockets) 33 | { 34 | [connectedSockets addObject:newSocket]; 35 | } 36 | NSLog(@"got connection"); 37 | NSString *initResponse = @"\x03WEL"; 38 | NSData *initResp = [initResponse dataUsingEncoding:NSASCIIStringEncoding]; 39 | [newSocket writeData:initResp withTimeout:-1 tag:0]; 40 | [newSocket readDataToLength:1 withTimeout:5 tag:0]; 41 | [self.parentVc connected]; 42 | } 43 | - (void)socket:(GCDAsyncSocket *)sock didWriteDataWithTag:(long)tag {} 44 | - (void)socket:(GCDAsyncSocket *)sock didReadData:(NSData *)data withTag:(long)tag { 45 | switch (tag) { 46 | case 0: { 47 | // length 48 | [sock readDataToLength:((uint8_t*)data.bytes)[0] withTimeout:1 tag:1]; 49 | break; 50 | } 51 | case 1: { 52 | // data 53 | if (data.length < 3) { 54 | [sock disconnect]; 55 | return; 56 | } 57 | NSData *msgData = [data subdataWithRange:NSMakeRange(0, 3)]; 58 | NSString *message = [[NSString alloc] initWithData:msgData encoding:NSASCIIStringEncoding]; 59 | if ([message isEqualToString:@"LED"] && data.length >= 99) { 60 | NSData *led = [data subdataWithRange:NSMakeRange(3, 96)]; 61 | [self.parentVc updateLed:led]; 62 | } 63 | 64 | [sock readDataToLength:1 withTimeout:5 tag:0]; 65 | } 66 | } 67 | } 68 | - (void)socketDidDisconnect:(GCDAsyncSocket *)sock withError:(NSError *)err { 69 | if (sock != server) 70 | { 71 | NSLog(@"connection ended"); 72 | @synchronized(connectedSockets) 73 | { 74 | [connectedSockets removeObject:sock]; 75 | if (connectedSockets.count == 0) { 76 | [self.parentVc disconnected]; 77 | } 78 | } 79 | } 80 | } 81 | 82 | - (void)BroadcastData:(NSData*)data { 83 | for (GCDAsyncSocket* sock in connectedSockets) { 84 | [sock writeData:data withTimeout:-1 tag:0]; 85 | } 86 | } 87 | 88 | - (void)becomeInactive { 89 | [self.parentVc becomeInactive]; 90 | server.IPv4Enabled = NO; 91 | server.IPv6Enabled = NO; 92 | for (GCDAsyncSocket* sock in connectedSockets) { 93 | [sock disconnect]; 94 | [connectedSockets removeObject:sock]; 95 | } 96 | [server disconnect]; 97 | } 98 | - (void)becomeActive { 99 | [self.parentVc becomeActive]; 100 | server.IPv4Enabled = YES; 101 | server.IPv6Enabled = YES; 102 | [self acceptConnection]; 103 | } 104 | 105 | @end 106 | 107 | -------------------------------------------------------------------------------- /Gemfile.lock: -------------------------------------------------------------------------------- 1 | GEM 2 | remote: https://rubygems.org/ 3 | specs: 4 | CFPropertyList (3.0.2) 5 | addressable (2.7.0) 6 | public_suffix (>= 2.0.2, < 5.0) 7 | atomos (0.1.3) 8 | babosa (1.0.3) 9 | claide (1.0.3) 10 | colored (1.2) 11 | colored2 (3.1.2) 12 | commander-fastlane (4.4.6) 13 | highline (~> 1.7.2) 14 | declarative (0.0.10) 15 | declarative-option (0.1.0) 16 | digest-crc (0.5.0) 17 | domain_name (0.5.20190701) 18 | unf (>= 0.0.5, < 1.0.0) 19 | dotenv (2.7.5) 20 | emoji_regex (1.0.1) 21 | excon (0.72.0) 22 | faraday (0.17.3) 23 | multipart-post (>= 1.2, < 3) 24 | faraday-cookie_jar (0.0.6) 25 | faraday (>= 0.7.4) 26 | http-cookie (~> 1.0.0) 27 | faraday_middleware (0.13.1) 28 | faraday (>= 0.7.4, < 1.0) 29 | fastimage (2.1.7) 30 | fastlane (2.142.0) 31 | CFPropertyList (>= 2.3, < 4.0.0) 32 | addressable (>= 2.3, < 3.0.0) 33 | babosa (>= 1.0.2, < 2.0.0) 34 | bundler (>= 1.12.0, < 3.0.0) 35 | colored 36 | commander-fastlane (>= 4.4.6, < 5.0.0) 37 | dotenv (>= 2.1.1, < 3.0.0) 38 | emoji_regex (>= 0.1, < 2.0) 39 | excon (>= 0.71.0, < 1.0.0) 40 | faraday (~> 0.17) 41 | faraday-cookie_jar (~> 0.0.6) 42 | faraday_middleware (~> 0.13.1) 43 | fastimage (>= 2.1.0, < 3.0.0) 44 | gh_inspector (>= 1.1.2, < 2.0.0) 45 | google-api-client (>= 0.29.2, < 0.37.0) 46 | google-cloud-storage (>= 1.15.0, < 2.0.0) 47 | highline (>= 1.7.2, < 2.0.0) 48 | json (< 3.0.0) 49 | jwt (~> 2.1.0) 50 | mini_magick (>= 4.9.4, < 5.0.0) 51 | multi_xml (~> 0.5) 52 | multipart-post (~> 2.0.0) 53 | plist (>= 3.1.0, < 4.0.0) 54 | public_suffix (~> 2.0.0) 55 | rubyzip (>= 1.3.0, < 2.0.0) 56 | security (= 0.1.3) 57 | simctl (~> 1.6.3) 58 | slack-notifier (>= 2.0.0, < 3.0.0) 59 | terminal-notifier (>= 2.0.0, < 3.0.0) 60 | terminal-table (>= 1.4.5, < 2.0.0) 61 | tty-screen (>= 0.6.3, < 1.0.0) 62 | tty-spinner (>= 0.8.0, < 1.0.0) 63 | word_wrap (~> 1.0.0) 64 | xcodeproj (>= 1.13.0, < 2.0.0) 65 | xcpretty (~> 0.3.0) 66 | xcpretty-travis-formatter (>= 0.0.3) 67 | gh_inspector (1.1.3) 68 | google-api-client (0.36.4) 69 | addressable (~> 2.5, >= 2.5.1) 70 | googleauth (~> 0.9) 71 | httpclient (>= 2.8.1, < 3.0) 72 | mini_mime (~> 1.0) 73 | representable (~> 3.0) 74 | retriable (>= 2.0, < 4.0) 75 | signet (~> 0.12) 76 | google-cloud-core (1.5.0) 77 | google-cloud-env (~> 1.0) 78 | google-cloud-errors (~> 1.0) 79 | google-cloud-env (1.3.1) 80 | faraday (>= 0.17.3, < 2.0) 81 | google-cloud-errors (1.0.0) 82 | google-cloud-storage (1.25.1) 83 | addressable (~> 2.5) 84 | digest-crc (~> 0.4) 85 | google-api-client (~> 0.33) 86 | google-cloud-core (~> 1.2) 87 | googleauth (~> 0.9) 88 | mini_mime (~> 1.0) 89 | googleauth (0.11.0) 90 | faraday (>= 0.17.3, < 2.0) 91 | jwt (>= 1.4, < 3.0) 92 | memoist (~> 0.16) 93 | multi_json (~> 1.11) 94 | os (>= 0.9, < 2.0) 95 | signet (~> 0.12) 96 | highline (1.7.10) 97 | http-cookie (1.0.3) 98 | domain_name (~> 0.5) 99 | httpclient (2.8.3) 100 | json (2.3.0) 101 | jwt (2.1.0) 102 | memoist (0.16.2) 103 | mini_magick (4.10.1) 104 | mini_mime (1.0.2) 105 | multi_json (1.14.1) 106 | multi_xml (0.6.0) 107 | multipart-post (2.0.0) 108 | nanaimo (0.2.6) 109 | naturally (2.2.0) 110 | os (1.0.1) 111 | plist (3.5.0) 112 | public_suffix (2.0.5) 113 | representable (3.0.4) 114 | declarative (< 0.1.0) 115 | declarative-option (< 0.2.0) 116 | uber (< 0.2.0) 117 | retriable (3.1.2) 118 | rouge (2.0.7) 119 | rubyzip (1.3.0) 120 | security (0.1.3) 121 | signet (0.13.0) 122 | addressable (~> 2.3) 123 | faraday (>= 0.17.3, < 2.0) 124 | jwt (>= 1.5, < 3.0) 125 | multi_json (~> 1.10) 126 | simctl (1.6.8) 127 | CFPropertyList 128 | naturally 129 | slack-notifier (2.3.2) 130 | terminal-notifier (2.0.0) 131 | terminal-table (1.8.0) 132 | unicode-display_width (~> 1.1, >= 1.1.1) 133 | tty-cursor (0.7.1) 134 | tty-screen (0.7.1) 135 | tty-spinner (0.9.3) 136 | tty-cursor (~> 0.7) 137 | uber (0.1.0) 138 | unf (0.1.4) 139 | unf_ext 140 | unf_ext (0.0.7.6) 141 | unicode-display_width (1.6.1) 142 | word_wrap (1.0.0) 143 | xcodeproj (1.15.0) 144 | CFPropertyList (>= 2.3.3, < 4.0) 145 | atomos (~> 0.1.3) 146 | claide (>= 1.0.2, < 2.0) 147 | colored2 (~> 3.1) 148 | nanaimo (~> 0.2.6) 149 | xcpretty (0.3.0) 150 | rouge (~> 2.0.7) 151 | xcpretty-travis-formatter (1.0.0) 152 | xcpretty (~> 0.2, >= 0.0.7) 153 | 154 | PLATFORMS 155 | ruby 156 | 157 | DEPENDENCIES 158 | fastlane 159 | 160 | BUNDLED WITH 161 | 2.0.2 162 | -------------------------------------------------------------------------------- /Pods/CocoaAsyncSocket/README.markdown: -------------------------------------------------------------------------------- 1 | # CocoaAsyncSocket 2 | [![Build Status](https://travis-ci.org/robbiehanson/CocoaAsyncSocket.svg?branch=master)](https://travis-ci.org/robbiehanson/CocoaAsyncSocket) [![Version Status](https://img.shields.io/cocoapods/v/CocoaAsyncSocket.svg?style=flat)](http://cocoadocs.org/docsets/CocoaAsyncSocket) [![Carthage compatible](https://img.shields.io/badge/Carthage-compatible-4BC51D.svg?style=flat)](https://github.com/Carthage/Carthage) [![Platform](http://img.shields.io/cocoapods/p/CocoaAsyncSocket.svg?style=flat)](http://cocoapods.org/?q=CocoaAsyncSocket) [![license Public Domain](https://img.shields.io/badge/license-Public%20Domain-orange.svg?style=flat)](https://en.wikipedia.org/wiki/Public_domain) 3 | 4 | 5 | CocoaAsyncSocket provides easy-to-use and powerful asynchronous socket libraries for Mac and iOS. The classes are described below. 6 | 7 | ## Installation 8 | 9 | #### CocoaPods 10 | 11 | Install using [CocoaPods](http://cocoapods.org) by adding this line to your Podfile: 12 | 13 | ````ruby 14 | use_frameworks! # Add this if you are targeting iOS 8+ or using Swift 15 | pod 'CocoaAsyncSocket' 16 | ```` 17 | 18 | #### Carthage 19 | 20 | CocoaAsyncSocket is [Carthage](https://github.com/Carthage/Carthage) compatible. To include it add the following line to your `Cartfile` 21 | 22 | ```bash 23 | github "robbiehanson/CocoaAsyncSocket" "master" 24 | ``` 25 | 26 | The project is currently configured to build for **iOS**, **tvOS** and **Mac**. After building with carthage the resultant frameworks will be stored in: 27 | 28 | * `Carthage/Build/iOS/CocoaAsyncSocket.framework` 29 | * `Carthage/Build/tvOS/CocoaAsyncSocket.framework` 30 | * `Carthage/Build/Mac/CocoaAsyncSocket.framework` 31 | 32 | Select the correct framework(s) and drag it into your project. 33 | 34 | #### Manual 35 | 36 | You can also include it into your project by adding the source files directly, but you should probably be using a dependency manager to keep up to date. 37 | 38 | ### Importing 39 | 40 | Using Objective-C: 41 | 42 | ```obj-c 43 | // When using iOS 8+ frameworks 44 | @import CocoaAsyncSocket; 45 | 46 | // OR when not using frameworks, targeting iOS 7 or below 47 | #import "GCDAsyncSocket.h" // for TCP 48 | #import "GCDAsyncUdpSocket.h" // for UDP 49 | ``` 50 | 51 | Using Swift: 52 | 53 | ```swift 54 | import CocoaAsyncSocket 55 | ``` 56 | 57 | ## TCP 58 | 59 | **GCDAsyncSocket** is a TCP/IP socket networking library built atop Grand Central Dispatch. Here are the key features available: 60 | 61 | - Native objective-c, fully self-contained in one class.
62 | _No need to muck around with sockets or streams. This class handles everything for you._ 63 | 64 | - Full delegate support
65 | _Errors, connections, read completions, write completions, progress, and disconnections all result in a call to your delegate method._ 66 | 67 | - Queued non-blocking reads and writes, with optional timeouts.
68 | _You tell it what to read or write, and it handles everything for you. Queueing, buffering, and searching for termination sequences within the stream - all handled for you automatically._ 69 | 70 | - Automatic socket acceptance.
71 | _Spin up a server socket, tell it to accept connections, and it will call you with new instances of itself for each connection._ 72 | 73 | - Support for TCP streams over IPv4 and IPv6.
74 | _Automatically connect to IPv4 or IPv6 hosts. Automatically accept incoming connections over both IPv4 and IPv6 with a single instance of this class. No more worrying about multiple sockets._ 75 | 76 | - Support for TLS / SSL
77 | _Secure your socket with ease using just a single method call. Available for both client and server sockets._ 78 | 79 | - Fully GCD based and Thread-Safe
80 | _It runs entirely within its own GCD dispatch_queue, and is completely thread-safe. Further, the delegate methods are all invoked asynchronously onto a dispatch_queue of your choosing. This means parallel operation of your socket code, and your delegate/processing code._ 81 | 82 | - The Latest Technology & Performance Optimizations
83 | _Internally the library takes advantage of technologies such as [kqueue's](http://en.wikipedia.org/wiki/Kqueue) to limit [system calls](http://en.wikipedia.org/wiki/System_call) and optimize buffer allocations. In other words, peak performance._ 84 | 85 | ## UDP 86 | 87 | **GCDAsyncUdpSocket** is a UDP/IP socket networking library built atop Grand Central Dispatch. Here are the key features available: 88 | 89 | - Native objective-c, fully self-contained in one class.
90 | _No need to muck around with low-level sockets. This class handles everything for you._ 91 | 92 | - Full delegate support.
93 | _Errors, send completions, receive completions, and disconnections all result in a call to your delegate method._ 94 | 95 | - Queued non-blocking send and receive operations, with optional timeouts.
96 | _You tell it what to send or receive, and it handles everything for you. Queueing, buffering, waiting and checking errno - all handled for you automatically._ 97 | 98 | - Support for IPv4 and IPv6.
99 | _Automatically send/recv using IPv4 and/or IPv6. No more worrying about multiple sockets._ 100 | 101 | - Fully GCD based and Thread-Safe
102 | _It runs entirely within its own GCD dispatch_queue, and is completely thread-safe. Further, the delegate methods are all invoked asynchronously onto a dispatch_queue of your choosing. This means parallel operation of your socket code, and your delegate/processing code._ 103 | 104 | *** 105 | 106 | For those new(ish) to networking, it's recommended you **[read the wiki](https://github.com/robbiehanson/CocoaAsyncSocket/wiki)**.
_Sockets might not work exactly like you think they do..._ 107 | 108 | **Still got questions?** Try the **[CocoaAsyncSocket Mailing List](http://groups.google.com/group/cocoaasyncsocket)**. 109 | *** 110 | 111 | Love the project? Wanna buy me a ☕️  ? (or a 🍺  😀 ): 112 | 113 | [![donation-bitcoin](https://bitpay.com/img/donate-sm.png)](https://onename.com/robbiehanson) 114 | [![donation-paypal](https://www.paypal.com/en_US/i/btn/btn_donate_SM.gif)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=2M8C699FQ8AW2) 115 | 116 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS-resources.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | set -u 4 | set -o pipefail 5 | 6 | if [ -z ${UNLOCALIZED_RESOURCES_FOLDER_PATH+x} ]; then 7 | # If UNLOCALIZED_RESOURCES_FOLDER_PATH is not set, then there's nowhere for us to copy 8 | # resources to, so exit 0 (signalling the script phase was successful). 9 | exit 0 10 | fi 11 | 12 | mkdir -p "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 13 | 14 | RESOURCES_TO_COPY=${PODS_ROOT}/resources-to-copy-${TARGETNAME}.txt 15 | > "$RESOURCES_TO_COPY" 16 | 17 | XCASSET_FILES=() 18 | 19 | # This protects against multiple targets copying the same framework dependency at the same time. The solution 20 | # was originally proposed here: https://lists.samba.org/archive/rsync/2008-February/020158.html 21 | RSYNC_PROTECT_TMP_FILES=(--filter "P .*.??????") 22 | 23 | case "${TARGETED_DEVICE_FAMILY:-}" in 24 | 1,2) 25 | TARGET_DEVICE_ARGS="--target-device ipad --target-device iphone" 26 | ;; 27 | 1) 28 | TARGET_DEVICE_ARGS="--target-device iphone" 29 | ;; 30 | 2) 31 | TARGET_DEVICE_ARGS="--target-device ipad" 32 | ;; 33 | 3) 34 | TARGET_DEVICE_ARGS="--target-device tv" 35 | ;; 36 | 4) 37 | TARGET_DEVICE_ARGS="--target-device watch" 38 | ;; 39 | *) 40 | TARGET_DEVICE_ARGS="--target-device mac" 41 | ;; 42 | esac 43 | 44 | install_resource() 45 | { 46 | if [[ "$1" = /* ]] ; then 47 | RESOURCE_PATH="$1" 48 | else 49 | RESOURCE_PATH="${PODS_ROOT}/$1" 50 | fi 51 | if [[ ! -e "$RESOURCE_PATH" ]] ; then 52 | cat << EOM 53 | error: Resource "$RESOURCE_PATH" not found. Run 'pod install' to update the copy resources script. 54 | EOM 55 | exit 1 56 | fi 57 | case $RESOURCE_PATH in 58 | *.storyboard) 59 | echo "ibtool --reference-external-strings-file --errors --warnings --notices --minimum-deployment-target ${!DEPLOYMENT_TARGET_SETTING_NAME} --output-format human-readable-text --compile ${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$RESOURCE_PATH\" .storyboard`.storyboardc $RESOURCE_PATH --sdk ${SDKROOT} ${TARGET_DEVICE_ARGS}" || true 60 | ibtool --reference-external-strings-file --errors --warnings --notices --minimum-deployment-target ${!DEPLOYMENT_TARGET_SETTING_NAME} --output-format human-readable-text --compile "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$RESOURCE_PATH\" .storyboard`.storyboardc" "$RESOURCE_PATH" --sdk "${SDKROOT}" ${TARGET_DEVICE_ARGS} 61 | ;; 62 | *.xib) 63 | echo "ibtool --reference-external-strings-file --errors --warnings --notices --minimum-deployment-target ${!DEPLOYMENT_TARGET_SETTING_NAME} --output-format human-readable-text --compile ${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$RESOURCE_PATH\" .xib`.nib $RESOURCE_PATH --sdk ${SDKROOT} ${TARGET_DEVICE_ARGS}" || true 64 | ibtool --reference-external-strings-file --errors --warnings --notices --minimum-deployment-target ${!DEPLOYMENT_TARGET_SETTING_NAME} --output-format human-readable-text --compile "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename \"$RESOURCE_PATH\" .xib`.nib" "$RESOURCE_PATH" --sdk "${SDKROOT}" ${TARGET_DEVICE_ARGS} 65 | ;; 66 | *.framework) 67 | echo "mkdir -p ${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" || true 68 | mkdir -p "${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 69 | echo "rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" $RESOURCE_PATH ${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" || true 70 | rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" "$RESOURCE_PATH" "${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 71 | ;; 72 | *.xcdatamodel) 73 | echo "xcrun momc \"$RESOURCE_PATH\" \"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH"`.mom\"" || true 74 | xcrun momc "$RESOURCE_PATH" "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH" .xcdatamodel`.mom" 75 | ;; 76 | *.xcdatamodeld) 77 | echo "xcrun momc \"$RESOURCE_PATH\" \"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH" .xcdatamodeld`.momd\"" || true 78 | xcrun momc "$RESOURCE_PATH" "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH" .xcdatamodeld`.momd" 79 | ;; 80 | *.xcmappingmodel) 81 | echo "xcrun mapc \"$RESOURCE_PATH\" \"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH" .xcmappingmodel`.cdm\"" || true 82 | xcrun mapc "$RESOURCE_PATH" "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/`basename "$RESOURCE_PATH" .xcmappingmodel`.cdm" 83 | ;; 84 | *.xcassets) 85 | ABSOLUTE_XCASSET_FILE="$RESOURCE_PATH" 86 | XCASSET_FILES+=("$ABSOLUTE_XCASSET_FILE") 87 | ;; 88 | *) 89 | echo "$RESOURCE_PATH" || true 90 | echo "$RESOURCE_PATH" >> "$RESOURCES_TO_COPY" 91 | ;; 92 | esac 93 | } 94 | 95 | mkdir -p "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 96 | rsync -avr --copy-links --no-relative --exclude '*/.svn/*' --files-from="$RESOURCES_TO_COPY" / "${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 97 | if [[ "${ACTION}" == "install" ]] && [[ "${SKIP_INSTALL}" == "NO" ]]; then 98 | mkdir -p "${INSTALL_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 99 | rsync -avr --copy-links --no-relative --exclude '*/.svn/*' --files-from="$RESOURCES_TO_COPY" / "${INSTALL_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 100 | fi 101 | rm -f "$RESOURCES_TO_COPY" 102 | 103 | if [[ -n "${WRAPPER_EXTENSION}" ]] && [ "`xcrun --find actool`" ] && [ -n "${XCASSET_FILES:-}" ] 104 | then 105 | # Find all other xcassets (this unfortunately includes those of path pods and other targets). 106 | OTHER_XCASSETS=$(find "$PWD" -iname "*.xcassets" -type d) 107 | while read line; do 108 | if [[ $line != "${PODS_ROOT}*" ]]; then 109 | XCASSET_FILES+=("$line") 110 | fi 111 | done <<<"$OTHER_XCASSETS" 112 | 113 | if [ -z ${ASSETCATALOG_COMPILER_APPICON_NAME+x} ]; then 114 | printf "%s\0" "${XCASSET_FILES[@]}" | xargs -0 xcrun actool --output-format human-readable-text --notices --warnings --platform "${PLATFORM_NAME}" --minimum-deployment-target "${!DEPLOYMENT_TARGET_SETTING_NAME}" ${TARGET_DEVICE_ARGS} --compress-pngs --compile "${BUILT_PRODUCTS_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" 115 | else 116 | printf "%s\0" "${XCASSET_FILES[@]}" | xargs -0 xcrun actool --output-format human-readable-text --notices --warnings --platform "${PLATFORM_NAME}" --minimum-deployment-target "${!DEPLOYMENT_TARGET_SETTING_NAME}" ${TARGET_DEVICE_ARGS} --compress-pngs --compile "${BUILT_PRODUCTS_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}" --app-icon "${ASSETCATALOG_COMPILER_APPICON_NAME}" --output-partial-info-plist "${TARGET_TEMP_DIR}/assetcatalog_generated_info_cocoapods.plist" 117 | fi 118 | fi 119 | -------------------------------------------------------------------------------- /Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS-frameworks.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | set -u 4 | set -o pipefail 5 | 6 | if [ -z ${FRAMEWORKS_FOLDER_PATH+x} ]; then 7 | # If FRAMEWORKS_FOLDER_PATH is not set, then there's nowhere for us to copy 8 | # frameworks to, so exit 0 (signalling the script phase was successful). 9 | exit 0 10 | fi 11 | 12 | echo "mkdir -p ${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 13 | mkdir -p "${CONFIGURATION_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 14 | 15 | COCOAPODS_PARALLEL_CODE_SIGN="${COCOAPODS_PARALLEL_CODE_SIGN:-false}" 16 | SWIFT_STDLIB_PATH="${DT_TOOLCHAIN_DIR}/usr/lib/swift/${PLATFORM_NAME}" 17 | 18 | # Used as a return value for each invocation of `strip_invalid_archs` function. 19 | STRIP_BINARY_RETVAL=0 20 | 21 | # This protects against multiple targets copying the same framework dependency at the same time. The solution 22 | # was originally proposed here: https://lists.samba.org/archive/rsync/2008-February/020158.html 23 | RSYNC_PROTECT_TMP_FILES=(--filter "P .*.??????") 24 | 25 | # Copies and strips a vendored framework 26 | install_framework() 27 | { 28 | if [ -r "${BUILT_PRODUCTS_DIR}/$1" ]; then 29 | local source="${BUILT_PRODUCTS_DIR}/$1" 30 | elif [ -r "${BUILT_PRODUCTS_DIR}/$(basename "$1")" ]; then 31 | local source="${BUILT_PRODUCTS_DIR}/$(basename "$1")" 32 | elif [ -r "$1" ]; then 33 | local source="$1" 34 | fi 35 | 36 | local destination="${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}" 37 | 38 | if [ -L "${source}" ]; then 39 | echo "Symlinked..." 40 | source="$(readlink "${source}")" 41 | fi 42 | 43 | # Use filter instead of exclude so missing patterns don't throw errors. 44 | echo "rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter \"- CVS/\" --filter \"- .svn/\" --filter \"- .git/\" --filter \"- .hg/\" --filter \"- Headers\" --filter \"- PrivateHeaders\" --filter \"- Modules\" \"${source}\" \"${destination}\"" 45 | rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter "- CVS/" --filter "- .svn/" --filter "- .git/" --filter "- .hg/" --filter "- Headers" --filter "- PrivateHeaders" --filter "- Modules" "${source}" "${destination}" 46 | 47 | local basename 48 | basename="$(basename -s .framework "$1")" 49 | binary="${destination}/${basename}.framework/${basename}" 50 | if ! [ -r "$binary" ]; then 51 | binary="${destination}/${basename}" 52 | fi 53 | 54 | # Strip invalid architectures so "fat" simulator / device frameworks work on device 55 | if [[ "$(file "$binary")" == *"dynamically linked shared library"* ]]; then 56 | strip_invalid_archs "$binary" 57 | fi 58 | 59 | # Resign the code if required by the build settings to avoid unstable apps 60 | code_sign_if_enabled "${destination}/$(basename "$1")" 61 | 62 | # Embed linked Swift runtime libraries. No longer necessary as of Xcode 7. 63 | if [ "${XCODE_VERSION_MAJOR}" -lt 7 ]; then 64 | local swift_runtime_libs 65 | swift_runtime_libs=$(xcrun otool -LX "$binary" | grep --color=never @rpath/libswift | sed -E s/@rpath\\/\(.+dylib\).*/\\1/g | uniq -u && exit ${PIPESTATUS[0]}) 66 | for lib in $swift_runtime_libs; do 67 | echo "rsync -auv \"${SWIFT_STDLIB_PATH}/${lib}\" \"${destination}\"" 68 | rsync -auv "${SWIFT_STDLIB_PATH}/${lib}" "${destination}" 69 | code_sign_if_enabled "${destination}/${lib}" 70 | done 71 | fi 72 | } 73 | 74 | # Copies and strips a vendored dSYM 75 | install_dsym() { 76 | local source="$1" 77 | if [ -r "$source" ]; then 78 | # Copy the dSYM into a the targets temp dir. 79 | echo "rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter \"- CVS/\" --filter \"- .svn/\" --filter \"- .git/\" --filter \"- .hg/\" --filter \"- Headers\" --filter \"- PrivateHeaders\" --filter \"- Modules\" \"${source}\" \"${DERIVED_FILES_DIR}\"" 80 | rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter "- CVS/" --filter "- .svn/" --filter "- .git/" --filter "- .hg/" --filter "- Headers" --filter "- PrivateHeaders" --filter "- Modules" "${source}" "${DERIVED_FILES_DIR}" 81 | 82 | local basename 83 | basename="$(basename -s .framework.dSYM "$source")" 84 | binary="${DERIVED_FILES_DIR}/${basename}.framework.dSYM/Contents/Resources/DWARF/${basename}" 85 | 86 | # Strip invalid architectures so "fat" simulator / device frameworks work on device 87 | if [[ "$(file "$binary")" == *"Mach-O dSYM companion"* ]]; then 88 | strip_invalid_archs "$binary" 89 | fi 90 | 91 | if [[ $STRIP_BINARY_RETVAL == 1 ]]; then 92 | # Move the stripped file into its final destination. 93 | echo "rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter \"- CVS/\" --filter \"- .svn/\" --filter \"- .git/\" --filter \"- .hg/\" --filter \"- Headers\" --filter \"- PrivateHeaders\" --filter \"- Modules\" \"${DERIVED_FILES_DIR}/${basename}.framework.dSYM\" \"${DWARF_DSYM_FOLDER_PATH}\"" 94 | rsync --delete -av "${RSYNC_PROTECT_TMP_FILES[@]}" --filter "- CVS/" --filter "- .svn/" --filter "- .git/" --filter "- .hg/" --filter "- Headers" --filter "- PrivateHeaders" --filter "- Modules" "${DERIVED_FILES_DIR}/${basename}.framework.dSYM" "${DWARF_DSYM_FOLDER_PATH}" 95 | else 96 | # The dSYM was not stripped at all, in this case touch a fake folder so the input/output paths from Xcode do not reexecute this script because the file is missing. 97 | touch "${DWARF_DSYM_FOLDER_PATH}/${basename}.framework.dSYM" 98 | fi 99 | fi 100 | } 101 | 102 | # Signs a framework with the provided identity 103 | code_sign_if_enabled() { 104 | if [ -n "${EXPANDED_CODE_SIGN_IDENTITY}" -a "${CODE_SIGNING_REQUIRED:-}" != "NO" -a "${CODE_SIGNING_ALLOWED}" != "NO" ]; then 105 | # Use the current code_sign_identitiy 106 | echo "Code Signing $1 with Identity ${EXPANDED_CODE_SIGN_IDENTITY_NAME}" 107 | local code_sign_cmd="/usr/bin/codesign --force --sign ${EXPANDED_CODE_SIGN_IDENTITY} ${OTHER_CODE_SIGN_FLAGS:-} --preserve-metadata=identifier,entitlements '$1'" 108 | 109 | if [ "${COCOAPODS_PARALLEL_CODE_SIGN}" == "true" ]; then 110 | code_sign_cmd="$code_sign_cmd &" 111 | fi 112 | echo "$code_sign_cmd" 113 | eval "$code_sign_cmd" 114 | fi 115 | } 116 | 117 | # Strip invalid architectures 118 | strip_invalid_archs() { 119 | binary="$1" 120 | # Get architectures for current target binary 121 | binary_archs="$(lipo -info "$binary" | rev | cut -d ':' -f1 | awk '{$1=$1;print}' | rev)" 122 | # Intersect them with the architectures we are building for 123 | intersected_archs="$(echo ${ARCHS[@]} ${binary_archs[@]} | tr ' ' '\n' | sort | uniq -d)" 124 | # If there are no archs supported by this binary then warn the user 125 | if [[ -z "$intersected_archs" ]]; then 126 | echo "warning: [CP] Vendored binary '$binary' contains architectures ($binary_archs) none of which match the current build architectures ($ARCHS)." 127 | STRIP_BINARY_RETVAL=0 128 | return 129 | fi 130 | stripped="" 131 | for arch in $binary_archs; do 132 | if ! [[ "${ARCHS}" == *"$arch"* ]]; then 133 | # Strip non-valid architectures in-place 134 | lipo -remove "$arch" -output "$binary" "$binary" || exit 1 135 | stripped="$stripped $arch" 136 | fi 137 | done 138 | if [[ "$stripped" ]]; then 139 | echo "Stripped $binary of architectures:$stripped" 140 | fi 141 | STRIP_BINARY_RETVAL=1 142 | } 143 | 144 | if [ "${COCOAPODS_PARALLEL_CODE_SIGN}" == "true" ]; then 145 | wait 146 | fi 147 | -------------------------------------------------------------------------------- /Brokenithm-iOS/ViewController.m: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.m 3 | // Brokenithm-iOS 4 | // 5 | // Created by ester on 2020/2/28. 6 | // Copyright © 2020 esterTion. All rights reserved. 7 | // 8 | 9 | #import "ViewController.h" 10 | #import "FunctionButton.h" 11 | 12 | @interface ViewController () { 13 | BOOL pendingHideStatus; 14 | } 15 | 16 | @end 17 | 18 | #define FUNCTION_MENU_HEIGHT 360.0f 19 | 20 | @implementation ViewController 21 | 22 | - (void)viewDidLoad { 23 | [super viewDidLoad]; 24 | pendingHideStatus = NO; 25 | [NSUserDefaults.standardUserDefaults registerDefaults:@{ 26 | @"enableAir": @YES, 27 | @"autoPopMenu": @YES, 28 | @"invertAir": @NO, 29 | @"menuDuration": @1.0 30 | }]; 31 | funcViewOn = YES; 32 | openCloseEventOnce = NO; 33 | 34 | // network permission 35 | /* 36 | { 37 | NSURLRequest *req = [NSURLRequest requestWithURL:[NSURL URLWithString:@"http://captive.apple.com/"]]; 38 | [NSURLConnection sendAsynchronousRequest:req 39 | queue:[NSOperationQueue mainQueue] 40 | completionHandler:^(NSURLResponse *resp, NSData *data, NSError *error) {}]; 41 | } 42 | */ 43 | 44 | // io view 45 | CGRect screenSize = [UIScreen mainScreen].bounds; 46 | screenWidth = screenSize.size.width; 47 | screenHeight = screenSize.size.height; 48 | float sliderHeight = screenHeight; 49 | self.airIOView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, screenWidth, screenHeight*0.4)]; 50 | self.sliderIOView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, screenWidth, sliderHeight)]; 51 | self.airIOView.backgroundColor = [UIColor blackColor]; 52 | self.airIOView.layer.borderWidth = 1.0f; 53 | self.airIOView.layer.borderColor = [UIColor whiteColor].CGColor; 54 | self.sliderIOView.layer.borderWidth = 1.0f; 55 | self.sliderIOView.layer.borderColor = [UIColor whiteColor].CGColor; 56 | [self.view addSubview:self.sliderIOView]; 57 | [self.view addSubview:self.airIOView]; 58 | 59 | // connect status view 60 | connectStatusView = [[UILabel alloc] initWithFrame:CGRectMake(screenWidth - 200.0, screenHeight * 0.1, 200.0, 50.0)]; 61 | connectStatusView.userInteractionEnabled = false; 62 | connectStatusView.text = [[NSBundle mainBundle] localizedStringForKey:@"Not connected" value:@"" table:nil] 63 | ; 64 | connectStatusView.textAlignment = NSTextAlignmentCenter; 65 | connectStatusView.textColor = [UIColor whiteColor]; 66 | connectStatusView.numberOfLines = 1; 67 | connectStatusView.backgroundColor = [UIColor blackColor]; 68 | connectStatusView.layer.borderColor = [UIColor whiteColor].CGColor; 69 | connectStatusView.layer.borderWidth = 1.0; 70 | [self.view addSubview:connectStatusView]; 71 | 72 | // function button view 73 | { 74 | functionBtnView = [[UIView alloc] initWithFrame:CGRectMake(0, screenHeight*0.1, 250, FUNCTION_MENU_HEIGHT)]; 75 | [self.view addSubview:functionBtnView]; 76 | // open/close btn 77 | UIView *openCloseBtnBorder; 78 | openCloseBtnBorder = [[UIView alloc] initWithFrame:CGRectMake(195, 0, 55, 50)]; 79 | openCloseBtnBorder.backgroundColor = [UIColor blackColor]; 80 | openCloseBtnBorder.layer.borderColor = [UIColor whiteColor].CGColor; 81 | openCloseBtnBorder.layer.borderWidth = 1.0; 82 | openCloseBtnBorder.layer.cornerRadius = 5; 83 | [functionBtnView addSubview:openCloseBtnBorder]; 84 | openCloseBtn = [[UILabel alloc] initWithFrame:CGRectMake(5, 0, 50, 50)]; 85 | openCloseBtn.textColor = [UIColor whiteColor]; 86 | openCloseBtn.textAlignment = NSTextAlignmentCenter; 87 | openCloseBtn.text = @"◀"; 88 | openCloseBtn.font = [UIFont systemFontOfSize:30]; 89 | UITapGestureRecognizer *openCloseTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(closeFunc)]; 90 | openCloseHold = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(openOrCloseFunc)]; 91 | openCloseHold.minimumPressDuration = 1; 92 | [openCloseBtnBorder addGestureRecognizer:openCloseTap]; 93 | [openCloseBtnBorder addGestureRecognizer:openCloseHold]; 94 | [openCloseBtnBorder addSubview:openCloseBtn]; 95 | // functions 96 | { 97 | NSArray*> *functions = @[ 98 | @[@"test", @"TEST"], 99 | @[@"service", @"SERVICE"], 100 | @[@"coin", [[NSBundle mainBundle] localizedStringForKey:@"Insert Coin" value:@"" table:nil]], 101 | @[@"card", [[NSBundle mainBundle] localizedStringForKey:@"Read Card" value:@"" table:nil]] 102 | ]; 103 | float offset = 0; 104 | for (NSArray *item in functions) { 105 | FunctionButton *btn = [[FunctionButton alloc] initAtY:offset]; 106 | btn.name = item[0]; 107 | btn.text = item[1]; 108 | [functionBtnView addSubview:btn]; 109 | offset += 60; 110 | } 111 | UIView *enableAir; 112 | UILabel *enableAirLabel; 113 | enableAir = [[UIView alloc] initWithFrame:CGRectMake(0, offset, 200, 60)]; 114 | enableAir.backgroundColor = [UIColor blackColor]; 115 | enableAir.layer.borderColor = [UIColor whiteColor].CGColor; 116 | enableAir.layer.borderWidth = 1.0; 117 | [functionBtnView addSubview:enableAir]; 118 | enableAirLabel = [[UILabel alloc] initWithFrame:CGRectMake(0, 0, 130, 60)]; 119 | enableAirLabel.textAlignment = NSTextAlignmentRight; 120 | enableAirLabel.textColor = [UIColor whiteColor]; 121 | enableAirLabel.numberOfLines = 1; 122 | enableAirLabel.text = [[NSBundle mainBundle] localizedStringForKey:@"Enable Air Input" value:@"" table:nil]; 123 | [enableAir addSubview:enableAirLabel]; 124 | enableAirToggle = [[UISwitch alloc] initWithFrame:CGRectMake(135, 13, 50, 27)]; 125 | [enableAir addSubview:enableAirToggle]; 126 | offset += 60; 127 | 128 | FunctionButton *moreBtn = [[FunctionButton alloc] initAtY:offset]; 129 | offset += 60; 130 | moreBtn.name = @"more_setting_button"; 131 | moreBtn.text = [[NSBundle mainBundle] localizedStringForKey:@"More..." value:@"" table:nil]; 132 | moreBtn.userInteractionEnabled = YES; 133 | UITapGestureRecognizer *moreBtnTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(jumpToSetting)]; 134 | [moreBtn addGestureRecognizer:moreBtnTap]; 135 | [functionBtnView addSubview:moreBtn]; 136 | 137 | [self loadPrefs]; 138 | [enableAirToggle addTarget:self action:@selector(enableAirChanged) forControlEvents:UIControlEventValueChanged]; 139 | } 140 | } 141 | 142 | // led gradient layer 143 | ledBackground = [CAGradientLayer layer]; 144 | ledBackground.frame = CGRectMake(0, 0, screenWidth, sliderHeight); 145 | [self.sliderIOView.layer addSublayer:ledBackground]; 146 | ledBackground.startPoint = CGPointMake(1,0); 147 | ledBackground.endPoint = CGPointMake(0,0); 148 | ledBackground.actions = [NSDictionary dictionaryWithObject:[NSNull null] forKey:@"colors"]; 149 | { 150 | float pointOffset = 0; 151 | float gapSmall = 1.0/16/8, gapBig = 1.0/16*6/8; 152 | NSMutableArray *locations = [NSMutableArray arrayWithCapacity:49]; 153 | for (int i=0,off=-1; i<16; i++) { 154 | locations[++off] = [NSNumber numberWithFloat:pointOffset]; 155 | pointOffset += gapSmall; 156 | locations[++off] = [NSNumber numberWithFloat:pointOffset]; 157 | pointOffset += gapBig; 158 | locations[++off] = [NSNumber numberWithFloat:pointOffset]; 159 | pointOffset += gapSmall; 160 | } 161 | locations[48] = @1; 162 | ledBackground.locations = locations; 163 | } 164 | 165 | struct CGColor *gridBorderColor = [UIColor colorWithWhite:1.0 alpha:0.2].CGColor; 166 | float airOffset=0, airHeight = screenHeight*0.4/6; 167 | for (int i=0;i<6;i++) { 168 | UIView *airInput = [[UIView alloc] initWithFrame:CGRectMake(0, airOffset, screenWidth, airHeight)]; 169 | airInput.layer.borderWidth = 1.0f; 170 | airInput.layer.borderColor = gridBorderColor; 171 | airOffset += airHeight; 172 | [self.airIOView addSubview:airInput]; 173 | } 174 | 175 | float sliderWidth = screenWidth / 16, sliderOffset = 0; 176 | for (int i=0;i<16;i++) { 177 | UIView *sliderInput = [[UIView alloc] initWithFrame:CGRectMake(sliderOffset, 0, sliderWidth, sliderHeight)]; 178 | sliderInput.layer.borderWidth = 1.0f; 179 | sliderInput.layer.borderColor = gridBorderColor; 180 | sliderOffset += sliderWidth; 181 | [self.sliderIOView addSubview:sliderInput]; 182 | } 183 | 184 | server = [[SocketDelegate alloc] init]; 185 | server.parentVc = self; 186 | NSLog(@"server created"); 187 | } 188 | 189 | -(void)loadPrefs { 190 | // enable air 191 | BOOL pref = [NSUserDefaults.standardUserDefaults boolForKey:@"enableAir"]; 192 | [enableAirToggle setOn:pref animated:NO]; 193 | [self updateAirEnabled:pref]; 194 | 195 | // auto pop 196 | autoPopMenu = [NSUserDefaults.standardUserDefaults boolForKey:@"autoPopMenu"]; 197 | 198 | // invert air 199 | pref = [NSUserDefaults.standardUserDefaults boolForKey:@"invertAir"]; 200 | [self updateAirInverted:pref]; 201 | 202 | // hold duration 203 | menuHoldDuration = [NSUserDefaults.standardUserDefaults valueForKey:@"menuDuration"]; 204 | openCloseHold.minimumPressDuration = [menuHoldDuration floatValue]; 205 | } 206 | 207 | -(void)updateLed:(NSData*)rgbData { 208 | if (rgbData.length != 32*3) return; 209 | NSMutableArray *colorArr = [NSMutableArray arrayWithCapacity:33]; 210 | colorArr[0] = (__bridge id)([UIColor colorWithWhite:0 alpha:0].CGColor); 211 | uint8_t *rgb = (uint8_t*)rgbData.bytes; 212 | for (int i=0, off=0; i<32; i++) { 213 | float r = rgb[i*3+1], g = rgb[i*3+2], b = rgb[i*3]; 214 | r /= 255.0; 215 | g /= 255.0; 216 | b /= 255.0; 217 | UIColor *color = [UIColor colorWithRed:r green:g blue:b alpha:1]; 218 | colorArr[++off] = (__bridge id)color.CGColor; 219 | off += (i+1)&1; 220 | colorArr[off] = (__bridge id)color.CGColor; 221 | } 222 | ledBackground.colors = colorArr; 223 | [ledBackground setNeedsDisplay]; 224 | } 225 | -(void)enableAirChanged{ 226 | BOOL pref = enableAirToggle.on; 227 | [NSUserDefaults.standardUserDefaults setBool:pref forKey:@"enableAir"]; 228 | [self updateAirEnabled:pref]; 229 | 230 | uint8_t airConf[] = {4, 'A', 'I', 'R', pref}; 231 | NSData *airConfData = [NSData dataWithBytes:airConf length:sizeof(airConf)]; 232 | [server BroadcastData:airConfData]; 233 | } 234 | -(void)updateAirEnabled:(BOOL)enable { 235 | self.airIOView.hidden = !enable; 236 | airEnabled = enable; 237 | } 238 | 239 | -(void)updateAirInverted:(BOOL)invert { 240 | if (invertAir != invert) { 241 | CGRect screenSize = [UIScreen mainScreen].bounds; 242 | screenWidth = screenSize.size.width; 243 | screenHeight = screenSize.size.height; 244 | self.airIOView.frame = CGRectMake(0, invert ? screenHeight * 0.6 : 0, screenWidth, screenHeight * 0.4); 245 | invertAir = invert; 246 | } 247 | } 248 | 249 | -(void)openOrCloseFunc { 250 | if (self->touchCount > 1) return; 251 | if (funcViewOn) { 252 | [self closeFunc]; 253 | } else { 254 | [self openFunc]; 255 | } 256 | } 257 | -(void)closeFunc { 258 | if (!openCloseEventOnce && funcViewOn) { 259 | funcViewOn = NO; 260 | openCloseEventOnce = YES; 261 | [UIView animateWithDuration:0.3 animations:^{ 262 | self->functionBtnView.frame = CGRectMake(-200, self->screenHeight*0.1, 250, FUNCTION_MENU_HEIGHT); 263 | }]; 264 | openCloseBtn.text = @"▶"; 265 | struct ioBuf buf = {0}; 266 | [self sendIoBuf:&buf]; 267 | } 268 | } 269 | -(void)openFunc { 270 | if (!openCloseEventOnce && !funcViewOn) { 271 | funcViewOn = YES; 272 | openCloseEventOnce = YES; 273 | [UIView animateWithDuration:0.3 animations:^{ 274 | self->functionBtnView.frame = CGRectMake(0, self->screenHeight*0.1, 250, FUNCTION_MENU_HEIGHT); 275 | }]; 276 | openCloseBtn.text = @"◀"; 277 | struct ioBuf buf = {0}; 278 | [self sendIoBuf:&buf]; 279 | } 280 | } 281 | -(void)jumpToSetting { 282 | [UIApplication.sharedApplication openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]]; 283 | } 284 | 285 | -(BOOL)prefersStatusBarHidden { return kCFCoreFoundationVersionNumber < 1443.00; } 286 | -(UIRectEdge)preferredScreenEdgesDeferringSystemGestures { return UIRectEdgeAll; } 287 | -(BOOL)prefersHomeIndicatorAutoHidden { return YES; } 288 | -(UIStatusBarStyle) preferredStatusBarStyle { return UIStatusBarStyleLightContent; } 289 | -(UIEditingInteractionConfiguration)editingInteractionConfiguration { return UIEditingInteractionConfigurationNone; } 290 | 291 | -(void)sendIoBuf:(struct ioBuf*)buf { 292 | buf->len = sizeof(*buf) - 1; 293 | buf->head[0] = 'I'; 294 | buf->head[1] = 'N'; 295 | buf->head[2] = 'P'; 296 | NSData* io = [NSData dataWithBytes:buf length:sizeof(*buf)]; 297 | [server BroadcastData:io]; 298 | } 299 | -(void)updateTouches:(UIEvent *)event { 300 | self->touchCount = event.allTouches.count; 301 | if (openCloseEventOnce) { 302 | if (event.allTouches.count == 1 && [event.allTouches anyObject].phase == UITouchPhaseEnded) { 303 | openCloseEventOnce = NO; 304 | } 305 | return; 306 | } 307 | float airHeight = screenHeight * 0.4; 308 | float airIOHeight = airHeight / 6; 309 | float sliderIOWidth = screenWidth / 16; 310 | struct ioBuf buf = {0}; 311 | for (UITouch *touch in event.allTouches) { 312 | UITouchPhase phase = touch.phase; 313 | if (phase == UITouchPhaseBegan || phase == UITouchPhaseMoved || phase == UITouchPhaseStationary) { 314 | if (funcViewOn) { 315 | CGPoint funcPoint = [touch locationInView:functionBtnView]; 316 | if (funcPoint.x > 0 && funcPoint.x < 200 && 317 | funcPoint.y > 0 && funcPoint.y < FUNCTION_MENU_HEIGHT) { 318 | if (funcPoint.y < 60) { 319 | buf.testBtn = 1; 320 | } else if (funcPoint.y < 120) { 321 | buf.serviceBtn = 1; 322 | } else if (funcPoint.y < 180) { 323 | if (phase == UITouchPhaseBegan) { 324 | uint8_t btnPress[] = {4, 'F', 'N', 'C', BNI_FUNCTION_COIN}; 325 | NSData *btnPressData = [NSData dataWithBytes:btnPress length:sizeof(btnPress)]; 326 | [server BroadcastData:btnPressData]; 327 | } 328 | } else if (funcPoint.y < 240) { 329 | if (phase == UITouchPhaseBegan) { 330 | uint8_t btnPress[] = {4, 'F', 'N', 'C', BNI_FUNCTION_CARD}; 331 | NSData *btnPressData = [NSData dataWithBytes:btnPress length:sizeof(btnPress)]; 332 | [server BroadcastData:btnPressData]; 333 | } 334 | } 335 | continue; 336 | } 337 | } 338 | CGPoint point = [touch locationInView:nil]; 339 | float pointX = screenWidth - point.x, pointY = point.y; 340 | BOOL inAirRange = airEnabled && ( 341 | (invertAir && pointY > screenHeight - airHeight) || 342 | (!invertAir && pointY < airHeight) 343 | ); 344 | if (inAirRange) { 345 | int idx; 346 | if (invertAir) { 347 | idx = (screenHeight - pointY) / airIOHeight; 348 | } else { 349 | idx = pointY / airIOHeight; 350 | } 351 | uint8_t airIdx[] = {4,5,2,3,0,1}; 352 | buf.air[airIdx[idx]] = 1; 353 | } else { 354 | float pointPos = pointX / sliderIOWidth; 355 | int idx = pointPos; 356 | if (idx > 15) idx = 15; 357 | int setIdx = idx*2; 358 | if (buf.slider[ setIdx ] != 0) { 359 | setIdx++; 360 | } 361 | buf.slider[ setIdx ] = 0x80; 362 | if (idx > 0) { if ((pointPos - idx) * 4 < 1) { 363 | setIdx = (idx - 1) * 2; 364 | if (buf.slider[ setIdx ] != 0) { 365 | setIdx++; 366 | } 367 | buf.slider[ setIdx ] = 0x80; 368 | } } else if (idx < 31) { if ((pointPos - idx) * 4 > 3) { 369 | setIdx = (idx + 1) * 2; 370 | if (buf.slider[ setIdx ] != 0) { 371 | setIdx++; 372 | } 373 | buf.slider[ setIdx ] = 0x80; 374 | } } 375 | } 376 | } 377 | } 378 | [self sendIoBuf:&buf]; 379 | } 380 | 381 | -(void)hideStatus { 382 | pendingHideStatus = NO; 383 | [UIView animateWithDuration:0.5 animations:^{ 384 | self->connectStatusView.frame = CGRectMake(self->screenWidth, self->screenHeight * 0.1, 200.0, 50.0); 385 | }]; 386 | } 387 | -(void)connected { 388 | connectStatusView.text = [[NSBundle mainBundle] localizedStringForKey:@"Connected" value:@"" table:nil]; 389 | [self performSelector:@selector(hideStatus) withObject:nil afterDelay:3]; 390 | pendingHideStatus = YES; 391 | 392 | uint8_t airConf[] = {4, 'A', 'I', 'R', airEnabled}; 393 | NSData *airConfData = [NSData dataWithBytes:airConf length:sizeof(airConf)]; 394 | [server BroadcastData:airConfData]; 395 | } 396 | -(void)disconnected { 397 | if (pendingHideStatus) { 398 | [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(hideStatus) object:nil]; 399 | } 400 | connectStatusView.text = [[NSBundle mainBundle] localizedStringForKey:@"Not connected" value:@"" table:nil]; 401 | [UIView animateWithDuration:0.3 animations:^{ 402 | self->connectStatusView.frame = CGRectMake(self->screenWidth - 200.0, self->screenHeight * 0.1, 200.0, 50.0); 403 | }]; 404 | if (autoPopMenu) { 405 | [self openFunc]; 406 | } 407 | } 408 | -(void)becomeInactive { 409 | struct ioBuf buf = {0}; 410 | [self sendIoBuf:&buf]; 411 | } 412 | -(void)becomeActive { 413 | [self loadPrefs]; 414 | } 415 | 416 | @end 417 | -------------------------------------------------------------------------------- /Brokenithm-iOS.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 50; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 1961EB742507451600C79BF8 /* Settings.bundle in Resources */ = {isa = PBXBuildFile; fileRef = 1961EB732507451600C79BF8 /* Settings.bundle */; }; 11 | 1968E72624086C2200784829 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 1968E72524086C2200784829 /* AppDelegate.m */; }; 12 | 1968E72924086C2200784829 /* ViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 1968E72824086C2200784829 /* ViewController.m */; }; 13 | 1968E72C24086C2200784829 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 1968E72A24086C2200784829 /* Main.storyboard */; }; 14 | 1968E72E24086C2B00784829 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 1968E72D24086C2B00784829 /* Assets.xcassets */; }; 15 | 1968E73424086C2B00784829 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 1968E73324086C2B00784829 /* main.m */; }; 16 | 19F13E2A240A6F2200809B83 /* SocketDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 19F13E29240A6F2200809B83 /* SocketDelegate.m */; }; 17 | 19F4071A240CFCFF00D7F506 /* MainApp.m in Sources */ = {isa = PBXBuildFile; fileRef = 19F40719240CFCFF00D7F506 /* MainApp.m */; }; 18 | 19F4071C240F8FCA00D7F506 /* FunctionButton.m in Sources */ = {isa = PBXBuildFile; fileRef = 19F4071B240F8FCA00D7F506 /* FunctionButton.m */; }; 19 | 19F40723240FE2B800D7F506 /* zh.lproj in Resources */ = {isa = PBXBuildFile; fileRef = 19F40722240FE2B700D7F506 /* zh.lproj */; }; 20 | D023549DD3B09C46EBA2E321 /* libPods-Brokenithm-iOS.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 5A7EE02147010843456A2152 /* libPods-Brokenithm-iOS.a */; }; 21 | /* End PBXBuildFile section */ 22 | 23 | /* Begin PBXFileReference section */ 24 | 1277586B240D1432002C27EE /* MainApp.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = MainApp.h; sourceTree = ""; }; 25 | 1961EB732507451600C79BF8 /* Settings.bundle */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.plug-in"; path = Settings.bundle; sourceTree = ""; }; 26 | 1968E72124086C2200784829 /* Brokenithm-iOS.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "Brokenithm-iOS.app"; sourceTree = BUILT_PRODUCTS_DIR; }; 27 | 1968E72424086C2200784829 /* AppDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = ""; }; 28 | 1968E72524086C2200784829 /* AppDelegate.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = AppDelegate.m; sourceTree = ""; }; 29 | 1968E72724086C2200784829 /* ViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ViewController.h; sourceTree = ""; }; 30 | 1968E72824086C2200784829 /* ViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ViewController.m; sourceTree = ""; }; 31 | 1968E72B24086C2200784829 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 32 | 1968E72D24086C2B00784829 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 33 | 1968E73224086C2B00784829 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 34 | 1968E73324086C2B00784829 /* main.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = ""; }; 35 | 19F13E22240A683200809B83 /* SocketDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SocketDelegate.h; sourceTree = ""; }; 36 | 19F13E29240A6F2200809B83 /* SocketDelegate.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = SocketDelegate.m; sourceTree = ""; }; 37 | 19F40719240CFCFF00D7F506 /* MainApp.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = MainApp.m; sourceTree = ""; }; 38 | 19F4071B240F8FCA00D7F506 /* FunctionButton.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = FunctionButton.m; sourceTree = ""; }; 39 | 19F4071D240F8FD600D7F506 /* FunctionButton.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = FunctionButton.h; sourceTree = ""; }; 40 | 19F40722240FE2B700D7F506 /* zh.lproj */ = {isa = PBXFileReference; lastKnownFileType = folder; path = zh.lproj; sourceTree = ""; }; 41 | 19F40724240FE52F00D7F506 /* zh */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = zh; path = zh.lproj/Main.strings; sourceTree = ""; }; 42 | 259804D4CC006A58255BC938 /* Pods-Brokenithm-iOS.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Brokenithm-iOS.release.xcconfig"; path = "Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS.release.xcconfig"; sourceTree = ""; }; 43 | 5A7EE02147010843456A2152 /* libPods-Brokenithm-iOS.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-Brokenithm-iOS.a"; sourceTree = BUILT_PRODUCTS_DIR; }; 44 | B78B36B35C6A90E4F71F84B4 /* Pods-Brokenithm-iOS.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Brokenithm-iOS.debug.xcconfig"; path = "Pods/Target Support Files/Pods-Brokenithm-iOS/Pods-Brokenithm-iOS.debug.xcconfig"; sourceTree = ""; }; 45 | /* End PBXFileReference section */ 46 | 47 | /* Begin PBXFrameworksBuildPhase section */ 48 | 1968E71E24086C2100784829 /* Frameworks */ = { 49 | isa = PBXFrameworksBuildPhase; 50 | buildActionMask = 2147483647; 51 | files = ( 52 | D023549DD3B09C46EBA2E321 /* libPods-Brokenithm-iOS.a in Frameworks */, 53 | ); 54 | runOnlyForDeploymentPostprocessing = 0; 55 | }; 56 | /* End PBXFrameworksBuildPhase section */ 57 | 58 | /* Begin PBXGroup section */ 59 | 1968E71824086C2100784829 = { 60 | isa = PBXGroup; 61 | children = ( 62 | 1968E72324086C2200784829 /* Brokenithm-iOS */, 63 | 1968E72224086C2200784829 /* Products */, 64 | DE2E731564C136C0C73A56CF /* Pods */, 65 | E73642D816ADA73C2E3B79FE /* Frameworks */, 66 | ); 67 | sourceTree = ""; 68 | }; 69 | 1968E72224086C2200784829 /* Products */ = { 70 | isa = PBXGroup; 71 | children = ( 72 | 1968E72124086C2200784829 /* Brokenithm-iOS.app */, 73 | ); 74 | name = Products; 75 | sourceTree = ""; 76 | }; 77 | 1968E72324086C2200784829 /* Brokenithm-iOS */ = { 78 | isa = PBXGroup; 79 | children = ( 80 | 19F40722240FE2B700D7F506 /* zh.lproj */, 81 | 1968E72424086C2200784829 /* AppDelegate.h */, 82 | 1968E72524086C2200784829 /* AppDelegate.m */, 83 | 19F4071D240F8FD600D7F506 /* FunctionButton.h */, 84 | 19F4071B240F8FCA00D7F506 /* FunctionButton.m */, 85 | 1277586B240D1432002C27EE /* MainApp.h */, 86 | 19F40719240CFCFF00D7F506 /* MainApp.m */, 87 | 1968E72724086C2200784829 /* ViewController.h */, 88 | 1968E72824086C2200784829 /* ViewController.m */, 89 | 1961EB732507451600C79BF8 /* Settings.bundle */, 90 | 1968E72A24086C2200784829 /* Main.storyboard */, 91 | 1968E72D24086C2B00784829 /* Assets.xcassets */, 92 | 1968E73224086C2B00784829 /* Info.plist */, 93 | 1968E73324086C2B00784829 /* main.m */, 94 | 19F13E22240A683200809B83 /* SocketDelegate.h */, 95 | 19F13E29240A6F2200809B83 /* SocketDelegate.m */, 96 | ); 97 | path = "Brokenithm-iOS"; 98 | sourceTree = ""; 99 | }; 100 | DE2E731564C136C0C73A56CF /* Pods */ = { 101 | isa = PBXGroup; 102 | children = ( 103 | B78B36B35C6A90E4F71F84B4 /* Pods-Brokenithm-iOS.debug.xcconfig */, 104 | 259804D4CC006A58255BC938 /* Pods-Brokenithm-iOS.release.xcconfig */, 105 | ); 106 | name = Pods; 107 | sourceTree = ""; 108 | }; 109 | E73642D816ADA73C2E3B79FE /* Frameworks */ = { 110 | isa = PBXGroup; 111 | children = ( 112 | 5A7EE02147010843456A2152 /* libPods-Brokenithm-iOS.a */, 113 | ); 114 | name = Frameworks; 115 | sourceTree = ""; 116 | }; 117 | /* End PBXGroup section */ 118 | 119 | /* Begin PBXNativeTarget section */ 120 | 1968E72024086C2100784829 /* Brokenithm-iOS */ = { 121 | isa = PBXNativeTarget; 122 | buildConfigurationList = 1968E73724086C2B00784829 /* Build configuration list for PBXNativeTarget "Brokenithm-iOS" */; 123 | buildPhases = ( 124 | 0542A5954C6F2FAC73EE7B2F /* [CP] Check Pods Manifest.lock */, 125 | 1968E71D24086C2100784829 /* Sources */, 126 | 1968E71E24086C2100784829 /* Frameworks */, 127 | 1968E71F24086C2100784829 /* Resources */, 128 | ); 129 | buildRules = ( 130 | ); 131 | dependencies = ( 132 | ); 133 | name = "Brokenithm-iOS"; 134 | productName = "Brokenithm-iOS"; 135 | productReference = 1968E72124086C2200784829 /* Brokenithm-iOS.app */; 136 | productType = "com.apple.product-type.application"; 137 | }; 138 | /* End PBXNativeTarget section */ 139 | 140 | /* Begin PBXProject section */ 141 | 1968E71924086C2100784829 /* Project object */ = { 142 | isa = PBXProject; 143 | attributes = { 144 | LastUpgradeCheck = 1010; 145 | ORGANIZATIONNAME = esterTion; 146 | TargetAttributes = { 147 | 1968E72024086C2100784829 = { 148 | CreatedOnToolsVersion = 10.1; 149 | }; 150 | }; 151 | }; 152 | buildConfigurationList = 1968E71C24086C2100784829 /* Build configuration list for PBXProject "Brokenithm-iOS" */; 153 | compatibilityVersion = "Xcode 9.3"; 154 | developmentRegion = en; 155 | hasScannedForEncodings = 0; 156 | knownRegions = ( 157 | en, 158 | Base, 159 | zh, 160 | ); 161 | mainGroup = 1968E71824086C2100784829; 162 | productRefGroup = 1968E72224086C2200784829 /* Products */; 163 | projectDirPath = ""; 164 | projectRoot = ""; 165 | targets = ( 166 | 1968E72024086C2100784829 /* Brokenithm-iOS */, 167 | ); 168 | }; 169 | /* End PBXProject section */ 170 | 171 | /* Begin PBXResourcesBuildPhase section */ 172 | 1968E71F24086C2100784829 /* Resources */ = { 173 | isa = PBXResourcesBuildPhase; 174 | buildActionMask = 2147483647; 175 | files = ( 176 | 1961EB742507451600C79BF8 /* Settings.bundle in Resources */, 177 | 1968E72E24086C2B00784829 /* Assets.xcassets in Resources */, 178 | 19F40723240FE2B800D7F506 /* zh.lproj in Resources */, 179 | 1968E72C24086C2200784829 /* Main.storyboard in Resources */, 180 | ); 181 | runOnlyForDeploymentPostprocessing = 0; 182 | }; 183 | /* End PBXResourcesBuildPhase section */ 184 | 185 | /* Begin PBXShellScriptBuildPhase section */ 186 | 0542A5954C6F2FAC73EE7B2F /* [CP] Check Pods Manifest.lock */ = { 187 | isa = PBXShellScriptBuildPhase; 188 | buildActionMask = 2147483647; 189 | files = ( 190 | ); 191 | inputPaths = ( 192 | "${PODS_PODFILE_DIR_PATH}/Podfile.lock", 193 | "${PODS_ROOT}/Manifest.lock", 194 | ); 195 | name = "[CP] Check Pods Manifest.lock"; 196 | outputPaths = ( 197 | "$(DERIVED_FILE_DIR)/Pods-Brokenithm-iOS-checkManifestLockResult.txt", 198 | ); 199 | runOnlyForDeploymentPostprocessing = 0; 200 | shellPath = /bin/sh; 201 | shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n"; 202 | showEnvVarsInLog = 0; 203 | }; 204 | /* End PBXShellScriptBuildPhase section */ 205 | 206 | /* Begin PBXSourcesBuildPhase section */ 207 | 1968E71D24086C2100784829 /* Sources */ = { 208 | isa = PBXSourcesBuildPhase; 209 | buildActionMask = 2147483647; 210 | files = ( 211 | 1968E72924086C2200784829 /* ViewController.m in Sources */, 212 | 19F4071C240F8FCA00D7F506 /* FunctionButton.m in Sources */, 213 | 1968E73424086C2B00784829 /* main.m in Sources */, 214 | 1968E72624086C2200784829 /* AppDelegate.m in Sources */, 215 | 19F4071A240CFCFF00D7F506 /* MainApp.m in Sources */, 216 | 19F13E2A240A6F2200809B83 /* SocketDelegate.m in Sources */, 217 | ); 218 | runOnlyForDeploymentPostprocessing = 0; 219 | }; 220 | /* End PBXSourcesBuildPhase section */ 221 | 222 | /* Begin PBXVariantGroup section */ 223 | 1968E72A24086C2200784829 /* Main.storyboard */ = { 224 | isa = PBXVariantGroup; 225 | children = ( 226 | 1968E72B24086C2200784829 /* Base */, 227 | 19F40724240FE52F00D7F506 /* zh */, 228 | ); 229 | name = Main.storyboard; 230 | sourceTree = ""; 231 | }; 232 | /* End PBXVariantGroup section */ 233 | 234 | /* Begin XCBuildConfiguration section */ 235 | 1968E73524086C2B00784829 /* Debug */ = { 236 | isa = XCBuildConfiguration; 237 | buildSettings = { 238 | ALWAYS_SEARCH_USER_PATHS = NO; 239 | CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; 240 | CLANG_ANALYZER_NONNULL = YES; 241 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 242 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 243 | CLANG_CXX_LIBRARY = "libc++"; 244 | CLANG_ENABLE_MODULES = YES; 245 | CLANG_ENABLE_OBJC_ARC = YES; 246 | CLANG_ENABLE_OBJC_WEAK = YES; 247 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 248 | CLANG_WARN_BOOL_CONVERSION = YES; 249 | CLANG_WARN_COMMA = YES; 250 | CLANG_WARN_CONSTANT_CONVERSION = YES; 251 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 252 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 253 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 254 | CLANG_WARN_EMPTY_BODY = YES; 255 | CLANG_WARN_ENUM_CONVERSION = YES; 256 | CLANG_WARN_INFINITE_RECURSION = YES; 257 | CLANG_WARN_INT_CONVERSION = YES; 258 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 259 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 260 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 261 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 262 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 263 | CLANG_WARN_STRICT_PROTOTYPES = YES; 264 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 265 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 266 | CLANG_WARN_UNREACHABLE_CODE = YES; 267 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 268 | CODE_SIGN_IDENTITY = "iPhone Developer"; 269 | COPY_PHASE_STRIP = NO; 270 | DEBUG_INFORMATION_FORMAT = dwarf; 271 | ENABLE_STRICT_OBJC_MSGSEND = YES; 272 | ENABLE_TESTABILITY = YES; 273 | GCC_C_LANGUAGE_STANDARD = gnu11; 274 | GCC_DYNAMIC_NO_PIC = NO; 275 | GCC_NO_COMMON_BLOCKS = YES; 276 | GCC_OPTIMIZATION_LEVEL = 0; 277 | GCC_PREPROCESSOR_DEFINITIONS = ( 278 | "DEBUG=1", 279 | "$(inherited)", 280 | ); 281 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 282 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 283 | GCC_WARN_UNDECLARED_SELECTOR = YES; 284 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 285 | GCC_WARN_UNUSED_FUNCTION = YES; 286 | GCC_WARN_UNUSED_VARIABLE = YES; 287 | IPHONEOS_DEPLOYMENT_TARGET = 12.1; 288 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 289 | MTL_FAST_MATH = YES; 290 | ONLY_ACTIVE_ARCH = YES; 291 | SDKROOT = iphoneos; 292 | }; 293 | name = Debug; 294 | }; 295 | 1968E73624086C2B00784829 /* Release */ = { 296 | isa = XCBuildConfiguration; 297 | buildSettings = { 298 | ALWAYS_SEARCH_USER_PATHS = NO; 299 | CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; 300 | CLANG_ANALYZER_NONNULL = YES; 301 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 302 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 303 | CLANG_CXX_LIBRARY = "libc++"; 304 | CLANG_ENABLE_MODULES = YES; 305 | CLANG_ENABLE_OBJC_ARC = YES; 306 | CLANG_ENABLE_OBJC_WEAK = YES; 307 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 308 | CLANG_WARN_BOOL_CONVERSION = YES; 309 | CLANG_WARN_COMMA = YES; 310 | CLANG_WARN_CONSTANT_CONVERSION = YES; 311 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 312 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 313 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 314 | CLANG_WARN_EMPTY_BODY = YES; 315 | CLANG_WARN_ENUM_CONVERSION = YES; 316 | CLANG_WARN_INFINITE_RECURSION = YES; 317 | CLANG_WARN_INT_CONVERSION = YES; 318 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 319 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 320 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 321 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 322 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 323 | CLANG_WARN_STRICT_PROTOTYPES = YES; 324 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 325 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 326 | CLANG_WARN_UNREACHABLE_CODE = YES; 327 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 328 | CODE_SIGN_IDENTITY = "iPhone Developer"; 329 | COPY_PHASE_STRIP = NO; 330 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 331 | ENABLE_NS_ASSERTIONS = NO; 332 | ENABLE_STRICT_OBJC_MSGSEND = YES; 333 | GCC_C_LANGUAGE_STANDARD = gnu11; 334 | GCC_NO_COMMON_BLOCKS = YES; 335 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 336 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 337 | GCC_WARN_UNDECLARED_SELECTOR = YES; 338 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 339 | GCC_WARN_UNUSED_FUNCTION = YES; 340 | GCC_WARN_UNUSED_VARIABLE = YES; 341 | IPHONEOS_DEPLOYMENT_TARGET = 12.1; 342 | MTL_ENABLE_DEBUG_INFO = NO; 343 | MTL_FAST_MATH = YES; 344 | SDKROOT = iphoneos; 345 | VALIDATE_PRODUCT = YES; 346 | }; 347 | name = Release; 348 | }; 349 | 1968E73824086C2B00784829 /* Debug */ = { 350 | isa = XCBuildConfiguration; 351 | baseConfigurationReference = B78B36B35C6A90E4F71F84B4 /* Pods-Brokenithm-iOS.debug.xcconfig */; 352 | buildSettings = { 353 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 354 | CODE_SIGN_IDENTITY = "Apple Development"; 355 | CODE_SIGN_STYLE = Automatic; 356 | CURRENT_PROJECT_VERSION = 11; 357 | DEVELOPMENT_TEAM = K9CP5766XY; 358 | INFOPLIST_FILE = "Brokenithm-iOS/Info.plist"; 359 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 360 | LD_RUNPATH_SEARCH_PATHS = ( 361 | "$(inherited)", 362 | "@executable_path/Frameworks", 363 | ); 364 | MARKETING_VERSION = 1.0; 365 | PRODUCT_BUNDLE_IDENTIFIER = com.estertion.brokenithm; 366 | PRODUCT_NAME = "$(TARGET_NAME)"; 367 | PROVISIONING_PROFILE_SPECIFIER = ""; 368 | TARGETED_DEVICE_FAMILY = "1,2"; 369 | VERSIONING_SYSTEM = "apple-generic"; 370 | }; 371 | name = Debug; 372 | }; 373 | 1968E73924086C2B00784829 /* Release */ = { 374 | isa = XCBuildConfiguration; 375 | baseConfigurationReference = 259804D4CC006A58255BC938 /* Pods-Brokenithm-iOS.release.xcconfig */; 376 | buildSettings = { 377 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 378 | CODE_SIGN_IDENTITY = "Apple Development"; 379 | CODE_SIGN_STYLE = Automatic; 380 | CURRENT_PROJECT_VERSION = 11; 381 | DEVELOPMENT_TEAM = K9CP5766XY; 382 | INFOPLIST_FILE = "Brokenithm-iOS/Info.plist"; 383 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 384 | LD_RUNPATH_SEARCH_PATHS = ( 385 | "$(inherited)", 386 | "@executable_path/Frameworks", 387 | ); 388 | MARKETING_VERSION = 1.0; 389 | PRODUCT_BUNDLE_IDENTIFIER = com.estertion.brokenithm; 390 | PRODUCT_NAME = "$(TARGET_NAME)"; 391 | PROVISIONING_PROFILE_SPECIFIER = ""; 392 | TARGETED_DEVICE_FAMILY = "1,2"; 393 | VERSIONING_SYSTEM = "apple-generic"; 394 | }; 395 | name = Release; 396 | }; 397 | /* End XCBuildConfiguration section */ 398 | 399 | /* Begin XCConfigurationList section */ 400 | 1968E71C24086C2100784829 /* Build configuration list for PBXProject "Brokenithm-iOS" */ = { 401 | isa = XCConfigurationList; 402 | buildConfigurations = ( 403 | 1968E73524086C2B00784829 /* Debug */, 404 | 1968E73624086C2B00784829 /* Release */, 405 | ); 406 | defaultConfigurationIsVisible = 0; 407 | defaultConfigurationName = Release; 408 | }; 409 | 1968E73724086C2B00784829 /* Build configuration list for PBXNativeTarget "Brokenithm-iOS" */ = { 410 | isa = XCConfigurationList; 411 | buildConfigurations = ( 412 | 1968E73824086C2B00784829 /* Debug */, 413 | 1968E73924086C2B00784829 /* Release */, 414 | ); 415 | defaultConfigurationIsVisible = 0; 416 | defaultConfigurationName = Release; 417 | }; 418 | /* End XCConfigurationList section */ 419 | }; 420 | rootObject = 1968E71924086C2100784829 /* Project object */; 421 | } 422 | -------------------------------------------------------------------------------- /Pods/Pods.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 50; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 06514FD84CC576BCCE44F89EE61A7F68 /* GCDAsyncSocket.h in Headers */ = {isa = PBXBuildFile; fileRef = C439B42C78960D0CD0C68788B8DC1C6B /* GCDAsyncSocket.h */; settings = {ATTRIBUTES = (Project, ); }; }; 11 | 28C627031DF7D0D6478AF95750C1D1A3 /* Pods-Brokenithm-iOS-dummy.m in Sources */ = {isa = PBXBuildFile; fileRef = 512DC49E972A73908F6EE4F51966BF0D /* Pods-Brokenithm-iOS-dummy.m */; }; 12 | 3A25A0B031EDD3B74BB39D3AD8967E3D /* GCDAsyncUdpSocket.m in Sources */ = {isa = PBXBuildFile; fileRef = FA9B822C6E137A44BCB98BDA5967BDE4 /* GCDAsyncUdpSocket.m */; settings = {COMPILER_FLAGS = "-DOS_OBJECT_USE_OBJC=0"; }; }; 13 | 4B3964B71F74D3D48482B3D853DA94E5 /* GCDAsyncSocket.m in Sources */ = {isa = PBXBuildFile; fileRef = 550CCDD8105A83A05D0BBF86D72816F5 /* GCDAsyncSocket.m */; settings = {COMPILER_FLAGS = "-DOS_OBJECT_USE_OBJC=0"; }; }; 14 | B0ED107F3AAF83FDD3035D0B3D864953 /* GCDAsyncUdpSocket.h in Headers */ = {isa = PBXBuildFile; fileRef = B658275E5FC3C66A7802C570535B242C /* GCDAsyncUdpSocket.h */; settings = {ATTRIBUTES = (Project, ); }; }; 15 | FA4347EF4A800F16CE57D834D4859D8D /* CocoaAsyncSocket-dummy.m in Sources */ = {isa = PBXBuildFile; fileRef = E45E4AA0570B7D99CCAC26D1EA82A982 /* CocoaAsyncSocket-dummy.m */; }; 16 | /* End PBXBuildFile section */ 17 | 18 | /* Begin PBXContainerItemProxy section */ 19 | 9C7C4EFAA0E49DF7EDADC652B4CEBCD5 /* PBXContainerItemProxy */ = { 20 | isa = PBXContainerItemProxy; 21 | containerPortal = BFDFE7DC352907FC980B868725387E98 /* Project object */; 22 | proxyType = 1; 23 | remoteGlobalIDString = 6083682834ABE0AE7BD1CBF06CADD036; 24 | remoteInfo = CocoaAsyncSocket; 25 | }; 26 | /* End PBXContainerItemProxy section */ 27 | 28 | /* Begin PBXFileReference section */ 29 | 0E34963F28F675CD369195619FFCED35 /* CocoaAsyncSocket-prefix.pch */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.h; path = "CocoaAsyncSocket-prefix.pch"; sourceTree = ""; }; 30 | 512DC49E972A73908F6EE4F51966BF0D /* Pods-Brokenithm-iOS-dummy.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; path = "Pods-Brokenithm-iOS-dummy.m"; sourceTree = ""; }; 31 | 550CCDD8105A83A05D0BBF86D72816F5 /* GCDAsyncSocket.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; name = GCDAsyncSocket.m; path = Source/GCD/GCDAsyncSocket.m; sourceTree = ""; }; 32 | 5F1D5C1CED575F0A78BDC49D12344AF3 /* libPods-Brokenithm-iOS.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; name = "libPods-Brokenithm-iOS.a"; path = "libPods-Brokenithm-iOS.a"; sourceTree = BUILT_PRODUCTS_DIR; }; 33 | 6CBEFE4F9E22AFDC6347A739BB35FF8C /* libCocoaAsyncSocket.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; name = libCocoaAsyncSocket.a; path = libCocoaAsyncSocket.a; sourceTree = BUILT_PRODUCTS_DIR; }; 34 | 8107E0304B553EAA2D2EAFF466DA7FF9 /* CocoaAsyncSocket.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = CocoaAsyncSocket.release.xcconfig; sourceTree = ""; }; 35 | 86AD2C54CD8661FCCC5D404CE6F55564 /* CocoaAsyncSocket.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = CocoaAsyncSocket.debug.xcconfig; sourceTree = ""; }; 36 | 9D940727FF8FB9C785EB98E56350EF41 /* Podfile */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; includeInIndex = 1; indentWidth = 2; lastKnownFileType = text; name = Podfile; path = ../Podfile; sourceTree = SOURCE_ROOT; tabWidth = 2; xcLanguageSpecificationIdentifier = xcode.lang.ruby; }; 37 | B658275E5FC3C66A7802C570535B242C /* GCDAsyncUdpSocket.h */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.h; name = GCDAsyncUdpSocket.h; path = Source/GCD/GCDAsyncUdpSocket.h; sourceTree = ""; }; 38 | C1FBED8A9679A642BF7E49E1C882D532 /* Pods-Brokenithm-iOS.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = "Pods-Brokenithm-iOS.debug.xcconfig"; sourceTree = ""; }; 39 | C439B42C78960D0CD0C68788B8DC1C6B /* GCDAsyncSocket.h */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.h; name = GCDAsyncSocket.h; path = Source/GCD/GCDAsyncSocket.h; sourceTree = ""; }; 40 | D13F256E635D9AD05D6765D12B37FE11 /* Pods-Brokenithm-iOS-acknowledgements.plist */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.plist.xml; path = "Pods-Brokenithm-iOS-acknowledgements.plist"; sourceTree = ""; }; 41 | D4199929834C40B261093F6D35DA4C51 /* Pods-Brokenithm-iOS.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = "Pods-Brokenithm-iOS.release.xcconfig"; sourceTree = ""; }; 42 | DF45A012C2DC19E1F82071A191017AFD /* Pods-Brokenithm-iOS-acknowledgements.markdown */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; path = "Pods-Brokenithm-iOS-acknowledgements.markdown"; sourceTree = ""; }; 43 | E45E4AA0570B7D99CCAC26D1EA82A982 /* CocoaAsyncSocket-dummy.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; path = "CocoaAsyncSocket-dummy.m"; sourceTree = ""; }; 44 | FA9B822C6E137A44BCB98BDA5967BDE4 /* GCDAsyncUdpSocket.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; name = GCDAsyncUdpSocket.m; path = Source/GCD/GCDAsyncUdpSocket.m; sourceTree = ""; }; 45 | /* End PBXFileReference section */ 46 | 47 | /* Begin PBXFrameworksBuildPhase section */ 48 | 20BA100C85EA53F9E47A90738553B93B /* Frameworks */ = { 49 | isa = PBXFrameworksBuildPhase; 50 | buildActionMask = 2147483647; 51 | files = ( 52 | ); 53 | runOnlyForDeploymentPostprocessing = 0; 54 | }; 55 | 7C863BEE7BA79C52CE29FF7DBEBD02B8 /* Frameworks */ = { 56 | isa = PBXFrameworksBuildPhase; 57 | buildActionMask = 2147483647; 58 | files = ( 59 | ); 60 | runOnlyForDeploymentPostprocessing = 0; 61 | }; 62 | /* End PBXFrameworksBuildPhase section */ 63 | 64 | /* Begin PBXGroup section */ 65 | 3A1E8691B67FC1D9ADB637E0C33E38BB /* Products */ = { 66 | isa = PBXGroup; 67 | children = ( 68 | 6CBEFE4F9E22AFDC6347A739BB35FF8C /* libCocoaAsyncSocket.a */, 69 | 5F1D5C1CED575F0A78BDC49D12344AF3 /* libPods-Brokenithm-iOS.a */, 70 | ); 71 | name = Products; 72 | sourceTree = ""; 73 | }; 74 | 64D78BE015C1199928207084C4C7C483 /* CocoaAsyncSocket */ = { 75 | isa = PBXGroup; 76 | children = ( 77 | C439B42C78960D0CD0C68788B8DC1C6B /* GCDAsyncSocket.h */, 78 | 550CCDD8105A83A05D0BBF86D72816F5 /* GCDAsyncSocket.m */, 79 | B658275E5FC3C66A7802C570535B242C /* GCDAsyncUdpSocket.h */, 80 | FA9B822C6E137A44BCB98BDA5967BDE4 /* GCDAsyncUdpSocket.m */, 81 | C2E6A04417A4BBD802945B171BCE6461 /* Support Files */, 82 | ); 83 | name = CocoaAsyncSocket; 84 | path = CocoaAsyncSocket; 85 | sourceTree = ""; 86 | }; 87 | 8E6F0D00AB9412ECD5F46632970B327B /* Targets Support Files */ = { 88 | isa = PBXGroup; 89 | children = ( 90 | 970BAB2FCC14DC0339D5182F9A7C35AF /* Pods-Brokenithm-iOS */, 91 | ); 92 | name = "Targets Support Files"; 93 | sourceTree = ""; 94 | }; 95 | 970BAB2FCC14DC0339D5182F9A7C35AF /* Pods-Brokenithm-iOS */ = { 96 | isa = PBXGroup; 97 | children = ( 98 | DF45A012C2DC19E1F82071A191017AFD /* Pods-Brokenithm-iOS-acknowledgements.markdown */, 99 | D13F256E635D9AD05D6765D12B37FE11 /* Pods-Brokenithm-iOS-acknowledgements.plist */, 100 | 512DC49E972A73908F6EE4F51966BF0D /* Pods-Brokenithm-iOS-dummy.m */, 101 | C1FBED8A9679A642BF7E49E1C882D532 /* Pods-Brokenithm-iOS.debug.xcconfig */, 102 | D4199929834C40B261093F6D35DA4C51 /* Pods-Brokenithm-iOS.release.xcconfig */, 103 | ); 104 | name = "Pods-Brokenithm-iOS"; 105 | path = "Target Support Files/Pods-Brokenithm-iOS"; 106 | sourceTree = ""; 107 | }; 108 | BB2BDAA8DB999C491DAC5EAE1CFDC78F /* Pods */ = { 109 | isa = PBXGroup; 110 | children = ( 111 | 64D78BE015C1199928207084C4C7C483 /* CocoaAsyncSocket */, 112 | ); 113 | name = Pods; 114 | sourceTree = ""; 115 | }; 116 | C2E6A04417A4BBD802945B171BCE6461 /* Support Files */ = { 117 | isa = PBXGroup; 118 | children = ( 119 | E45E4AA0570B7D99CCAC26D1EA82A982 /* CocoaAsyncSocket-dummy.m */, 120 | 0E34963F28F675CD369195619FFCED35 /* CocoaAsyncSocket-prefix.pch */, 121 | 86AD2C54CD8661FCCC5D404CE6F55564 /* CocoaAsyncSocket.debug.xcconfig */, 122 | 8107E0304B553EAA2D2EAFF466DA7FF9 /* CocoaAsyncSocket.release.xcconfig */, 123 | ); 124 | name = "Support Files"; 125 | path = "../Target Support Files/CocoaAsyncSocket"; 126 | sourceTree = ""; 127 | }; 128 | CF1408CF629C7361332E53B88F7BD30C = { 129 | isa = PBXGroup; 130 | children = ( 131 | 9D940727FF8FB9C785EB98E56350EF41 /* Podfile */, 132 | D89477F20FB1DE18A04690586D7808C4 /* Frameworks */, 133 | BB2BDAA8DB999C491DAC5EAE1CFDC78F /* Pods */, 134 | 3A1E8691B67FC1D9ADB637E0C33E38BB /* Products */, 135 | 8E6F0D00AB9412ECD5F46632970B327B /* Targets Support Files */, 136 | ); 137 | sourceTree = ""; 138 | }; 139 | D89477F20FB1DE18A04690586D7808C4 /* Frameworks */ = { 140 | isa = PBXGroup; 141 | children = ( 142 | ); 143 | name = Frameworks; 144 | sourceTree = ""; 145 | }; 146 | /* End PBXGroup section */ 147 | 148 | /* Begin PBXHeadersBuildPhase section */ 149 | 83268A4608982FCFF93FA48DCC883251 /* Headers */ = { 150 | isa = PBXHeadersBuildPhase; 151 | buildActionMask = 2147483647; 152 | files = ( 153 | 06514FD84CC576BCCE44F89EE61A7F68 /* GCDAsyncSocket.h in Headers */, 154 | B0ED107F3AAF83FDD3035D0B3D864953 /* GCDAsyncUdpSocket.h in Headers */, 155 | ); 156 | runOnlyForDeploymentPostprocessing = 0; 157 | }; 158 | A0A11C0BCA94BE60AAE0AA25D9287AD5 /* Headers */ = { 159 | isa = PBXHeadersBuildPhase; 160 | buildActionMask = 2147483647; 161 | files = ( 162 | ); 163 | runOnlyForDeploymentPostprocessing = 0; 164 | }; 165 | /* End PBXHeadersBuildPhase section */ 166 | 167 | /* Begin PBXNativeTarget section */ 168 | 6083682834ABE0AE7BD1CBF06CADD036 /* CocoaAsyncSocket */ = { 169 | isa = PBXNativeTarget; 170 | buildConfigurationList = BF535641E00BECC6FFAF53CFB25A8755 /* Build configuration list for PBXNativeTarget "CocoaAsyncSocket" */; 171 | buildPhases = ( 172 | 83268A4608982FCFF93FA48DCC883251 /* Headers */, 173 | A6B708BDDA38EEF515F2383D1BB1E85A /* Sources */, 174 | 20BA100C85EA53F9E47A90738553B93B /* Frameworks */, 175 | ); 176 | buildRules = ( 177 | ); 178 | dependencies = ( 179 | ); 180 | name = CocoaAsyncSocket; 181 | productName = CocoaAsyncSocket; 182 | productReference = 6CBEFE4F9E22AFDC6347A739BB35FF8C /* libCocoaAsyncSocket.a */; 183 | productType = "com.apple.product-type.library.static"; 184 | }; 185 | B29CA78F54FB472469638DC5F30D1B15 /* Pods-Brokenithm-iOS */ = { 186 | isa = PBXNativeTarget; 187 | buildConfigurationList = 4029633DCB83FD66D0CA78711DC8DFEF /* Build configuration list for PBXNativeTarget "Pods-Brokenithm-iOS" */; 188 | buildPhases = ( 189 | A0A11C0BCA94BE60AAE0AA25D9287AD5 /* Headers */, 190 | 0BDCD7A87E26D2161AC0277810AA9469 /* Sources */, 191 | 7C863BEE7BA79C52CE29FF7DBEBD02B8 /* Frameworks */, 192 | ); 193 | buildRules = ( 194 | ); 195 | dependencies = ( 196 | 3BBE15386742B7EB2E34332AFFF4DF42 /* PBXTargetDependency */, 197 | ); 198 | name = "Pods-Brokenithm-iOS"; 199 | productName = "Pods-Brokenithm-iOS"; 200 | productReference = 5F1D5C1CED575F0A78BDC49D12344AF3 /* libPods-Brokenithm-iOS.a */; 201 | productType = "com.apple.product-type.library.static"; 202 | }; 203 | /* End PBXNativeTarget section */ 204 | 205 | /* Begin PBXProject section */ 206 | BFDFE7DC352907FC980B868725387E98 /* Project object */ = { 207 | isa = PBXProject; 208 | attributes = { 209 | LastSwiftUpdateCheck = 1100; 210 | LastUpgradeCheck = 1100; 211 | }; 212 | buildConfigurationList = 4821239608C13582E20E6DA73FD5F1F9 /* Build configuration list for PBXProject "Pods" */; 213 | compatibilityVersion = "Xcode 9.3"; 214 | developmentRegion = en; 215 | hasScannedForEncodings = 0; 216 | knownRegions = ( 217 | en, 218 | Base, 219 | ); 220 | mainGroup = CF1408CF629C7361332E53B88F7BD30C; 221 | productRefGroup = 3A1E8691B67FC1D9ADB637E0C33E38BB /* Products */; 222 | projectDirPath = ""; 223 | projectRoot = ""; 224 | targets = ( 225 | 6083682834ABE0AE7BD1CBF06CADD036 /* CocoaAsyncSocket */, 226 | B29CA78F54FB472469638DC5F30D1B15 /* Pods-Brokenithm-iOS */, 227 | ); 228 | }; 229 | /* End PBXProject section */ 230 | 231 | /* Begin PBXSourcesBuildPhase section */ 232 | 0BDCD7A87E26D2161AC0277810AA9469 /* Sources */ = { 233 | isa = PBXSourcesBuildPhase; 234 | buildActionMask = 2147483647; 235 | files = ( 236 | 28C627031DF7D0D6478AF95750C1D1A3 /* Pods-Brokenithm-iOS-dummy.m in Sources */, 237 | ); 238 | runOnlyForDeploymentPostprocessing = 0; 239 | }; 240 | A6B708BDDA38EEF515F2383D1BB1E85A /* Sources */ = { 241 | isa = PBXSourcesBuildPhase; 242 | buildActionMask = 2147483647; 243 | files = ( 244 | FA4347EF4A800F16CE57D834D4859D8D /* CocoaAsyncSocket-dummy.m in Sources */, 245 | 4B3964B71F74D3D48482B3D853DA94E5 /* GCDAsyncSocket.m in Sources */, 246 | 3A25A0B031EDD3B74BB39D3AD8967E3D /* GCDAsyncUdpSocket.m in Sources */, 247 | ); 248 | runOnlyForDeploymentPostprocessing = 0; 249 | }; 250 | /* End PBXSourcesBuildPhase section */ 251 | 252 | /* Begin PBXTargetDependency section */ 253 | 3BBE15386742B7EB2E34332AFFF4DF42 /* PBXTargetDependency */ = { 254 | isa = PBXTargetDependency; 255 | name = CocoaAsyncSocket; 256 | target = 6083682834ABE0AE7BD1CBF06CADD036 /* CocoaAsyncSocket */; 257 | targetProxy = 9C7C4EFAA0E49DF7EDADC652B4CEBCD5 /* PBXContainerItemProxy */; 258 | }; 259 | /* End PBXTargetDependency section */ 260 | 261 | /* Begin XCBuildConfiguration section */ 262 | 2BAB697BF6B09E8232C79E9481F78A70 /* Debug */ = { 263 | isa = XCBuildConfiguration; 264 | baseConfigurationReference = 86AD2C54CD8661FCCC5D404CE6F55564 /* CocoaAsyncSocket.debug.xcconfig */; 265 | buildSettings = { 266 | CODE_SIGN_IDENTITY = "iPhone Developer"; 267 | "CODE_SIGN_IDENTITY[sdk=appletvos*]" = ""; 268 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; 269 | "CODE_SIGN_IDENTITY[sdk=watchos*]" = ""; 270 | GCC_PREFIX_HEADER = "Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket-prefix.pch"; 271 | IPHONEOS_DEPLOYMENT_TARGET = 5.0; 272 | OTHER_LDFLAGS = ""; 273 | OTHER_LIBTOOLFLAGS = ""; 274 | PRIVATE_HEADERS_FOLDER_PATH = ""; 275 | PRODUCT_MODULE_NAME = CocoaAsyncSocket; 276 | PRODUCT_NAME = CocoaAsyncSocket; 277 | PUBLIC_HEADERS_FOLDER_PATH = ""; 278 | SDKROOT = iphoneos; 279 | SKIP_INSTALL = YES; 280 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = "$(inherited) "; 281 | TARGETED_DEVICE_FAMILY = "1,2"; 282 | }; 283 | name = Debug; 284 | }; 285 | 4BE66A09A74FD25164AAB3C2645B9B93 /* Release */ = { 286 | isa = XCBuildConfiguration; 287 | buildSettings = { 288 | ALWAYS_SEARCH_USER_PATHS = NO; 289 | CLANG_ANALYZER_NONNULL = YES; 290 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 291 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 292 | CLANG_CXX_LIBRARY = "libc++"; 293 | CLANG_ENABLE_MODULES = YES; 294 | CLANG_ENABLE_OBJC_ARC = YES; 295 | CLANG_ENABLE_OBJC_WEAK = YES; 296 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 297 | CLANG_WARN_BOOL_CONVERSION = YES; 298 | CLANG_WARN_COMMA = YES; 299 | CLANG_WARN_CONSTANT_CONVERSION = YES; 300 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 301 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 302 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 303 | CLANG_WARN_EMPTY_BODY = YES; 304 | CLANG_WARN_ENUM_CONVERSION = YES; 305 | CLANG_WARN_INFINITE_RECURSION = YES; 306 | CLANG_WARN_INT_CONVERSION = YES; 307 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 308 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 309 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 310 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 311 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 312 | CLANG_WARN_STRICT_PROTOTYPES = YES; 313 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 314 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 315 | CLANG_WARN_UNREACHABLE_CODE = YES; 316 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 317 | COPY_PHASE_STRIP = NO; 318 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 319 | ENABLE_NS_ASSERTIONS = NO; 320 | ENABLE_STRICT_OBJC_MSGSEND = YES; 321 | GCC_C_LANGUAGE_STANDARD = gnu11; 322 | GCC_NO_COMMON_BLOCKS = YES; 323 | GCC_PREPROCESSOR_DEFINITIONS = ( 324 | "POD_CONFIGURATION_RELEASE=1", 325 | "$(inherited)", 326 | ); 327 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 328 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 329 | GCC_WARN_UNDECLARED_SELECTOR = YES; 330 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 331 | GCC_WARN_UNUSED_FUNCTION = YES; 332 | GCC_WARN_UNUSED_VARIABLE = YES; 333 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 334 | MTL_ENABLE_DEBUG_INFO = NO; 335 | MTL_FAST_MATH = YES; 336 | PRODUCT_NAME = "$(TARGET_NAME)"; 337 | STRIP_INSTALLED_PRODUCT = NO; 338 | SWIFT_COMPILATION_MODE = wholemodule; 339 | SWIFT_OPTIMIZATION_LEVEL = "-O"; 340 | SWIFT_VERSION = 5.0; 341 | SYMROOT = "${SRCROOT}/../build"; 342 | }; 343 | name = Release; 344 | }; 345 | 7EF7227D9B20A1D549000096ACCB23D7 /* Debug */ = { 346 | isa = XCBuildConfiguration; 347 | buildSettings = { 348 | ALWAYS_SEARCH_USER_PATHS = NO; 349 | CLANG_ANALYZER_NONNULL = YES; 350 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 351 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 352 | CLANG_CXX_LIBRARY = "libc++"; 353 | CLANG_ENABLE_MODULES = YES; 354 | CLANG_ENABLE_OBJC_ARC = YES; 355 | CLANG_ENABLE_OBJC_WEAK = YES; 356 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 357 | CLANG_WARN_BOOL_CONVERSION = YES; 358 | CLANG_WARN_COMMA = YES; 359 | CLANG_WARN_CONSTANT_CONVERSION = YES; 360 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 361 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 362 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 363 | CLANG_WARN_EMPTY_BODY = YES; 364 | CLANG_WARN_ENUM_CONVERSION = YES; 365 | CLANG_WARN_INFINITE_RECURSION = YES; 366 | CLANG_WARN_INT_CONVERSION = YES; 367 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 368 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 369 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 370 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 371 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 372 | CLANG_WARN_STRICT_PROTOTYPES = YES; 373 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 374 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 375 | CLANG_WARN_UNREACHABLE_CODE = YES; 376 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 377 | COPY_PHASE_STRIP = NO; 378 | DEBUG_INFORMATION_FORMAT = dwarf; 379 | ENABLE_STRICT_OBJC_MSGSEND = YES; 380 | ENABLE_TESTABILITY = YES; 381 | GCC_C_LANGUAGE_STANDARD = gnu11; 382 | GCC_DYNAMIC_NO_PIC = NO; 383 | GCC_NO_COMMON_BLOCKS = YES; 384 | GCC_OPTIMIZATION_LEVEL = 0; 385 | GCC_PREPROCESSOR_DEFINITIONS = ( 386 | "POD_CONFIGURATION_DEBUG=1", 387 | "DEBUG=1", 388 | "$(inherited)", 389 | ); 390 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 391 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 392 | GCC_WARN_UNDECLARED_SELECTOR = YES; 393 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 394 | GCC_WARN_UNUSED_FUNCTION = YES; 395 | GCC_WARN_UNUSED_VARIABLE = YES; 396 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 397 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 398 | MTL_FAST_MATH = YES; 399 | ONLY_ACTIVE_ARCH = YES; 400 | PRODUCT_NAME = "$(TARGET_NAME)"; 401 | STRIP_INSTALLED_PRODUCT = NO; 402 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 403 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 404 | SWIFT_VERSION = 5.0; 405 | SYMROOT = "${SRCROOT}/../build"; 406 | }; 407 | name = Debug; 408 | }; 409 | 8767D2E96CD99B0C6ACD2F35D6AB9988 /* Release */ = { 410 | isa = XCBuildConfiguration; 411 | baseConfigurationReference = D4199929834C40B261093F6D35DA4C51 /* Pods-Brokenithm-iOS.release.xcconfig */; 412 | buildSettings = { 413 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = NO; 414 | CODE_SIGN_IDENTITY = "iPhone Developer"; 415 | "CODE_SIGN_IDENTITY[sdk=appletvos*]" = ""; 416 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; 417 | "CODE_SIGN_IDENTITY[sdk=watchos*]" = ""; 418 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 419 | MACH_O_TYPE = staticlib; 420 | OTHER_LDFLAGS = ""; 421 | OTHER_LIBTOOLFLAGS = ""; 422 | PODS_ROOT = "$(SRCROOT)"; 423 | PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.${PRODUCT_NAME:rfc1034identifier}"; 424 | SDKROOT = iphoneos; 425 | SKIP_INSTALL = YES; 426 | TARGETED_DEVICE_FAMILY = "1,2"; 427 | VALIDATE_PRODUCT = YES; 428 | }; 429 | name = Release; 430 | }; 431 | 9A3244A0C1ED230D9CAF416848B3DAA9 /* Release */ = { 432 | isa = XCBuildConfiguration; 433 | baseConfigurationReference = 8107E0304B553EAA2D2EAFF466DA7FF9 /* CocoaAsyncSocket.release.xcconfig */; 434 | buildSettings = { 435 | CODE_SIGN_IDENTITY = "iPhone Developer"; 436 | "CODE_SIGN_IDENTITY[sdk=appletvos*]" = ""; 437 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; 438 | "CODE_SIGN_IDENTITY[sdk=watchos*]" = ""; 439 | GCC_PREFIX_HEADER = "Target Support Files/CocoaAsyncSocket/CocoaAsyncSocket-prefix.pch"; 440 | IPHONEOS_DEPLOYMENT_TARGET = 5.0; 441 | OTHER_LDFLAGS = ""; 442 | OTHER_LIBTOOLFLAGS = ""; 443 | PRIVATE_HEADERS_FOLDER_PATH = ""; 444 | PRODUCT_MODULE_NAME = CocoaAsyncSocket; 445 | PRODUCT_NAME = CocoaAsyncSocket; 446 | PUBLIC_HEADERS_FOLDER_PATH = ""; 447 | SDKROOT = iphoneos; 448 | SKIP_INSTALL = YES; 449 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = "$(inherited) "; 450 | TARGETED_DEVICE_FAMILY = "1,2"; 451 | VALIDATE_PRODUCT = YES; 452 | }; 453 | name = Release; 454 | }; 455 | EDBC8CEBD2AFC4A7AAD607967C2D61B9 /* Debug */ = { 456 | isa = XCBuildConfiguration; 457 | baseConfigurationReference = C1FBED8A9679A642BF7E49E1C882D532 /* Pods-Brokenithm-iOS.debug.xcconfig */; 458 | buildSettings = { 459 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = NO; 460 | CODE_SIGN_IDENTITY = "iPhone Developer"; 461 | "CODE_SIGN_IDENTITY[sdk=appletvos*]" = ""; 462 | "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; 463 | "CODE_SIGN_IDENTITY[sdk=watchos*]" = ""; 464 | IPHONEOS_DEPLOYMENT_TARGET = 8.0; 465 | MACH_O_TYPE = staticlib; 466 | OTHER_LDFLAGS = ""; 467 | OTHER_LIBTOOLFLAGS = ""; 468 | PODS_ROOT = "$(SRCROOT)"; 469 | PRODUCT_BUNDLE_IDENTIFIER = "org.cocoapods.${PRODUCT_NAME:rfc1034identifier}"; 470 | SDKROOT = iphoneos; 471 | SKIP_INSTALL = YES; 472 | TARGETED_DEVICE_FAMILY = "1,2"; 473 | }; 474 | name = Debug; 475 | }; 476 | /* End XCBuildConfiguration section */ 477 | 478 | /* Begin XCConfigurationList section */ 479 | 4029633DCB83FD66D0CA78711DC8DFEF /* Build configuration list for PBXNativeTarget "Pods-Brokenithm-iOS" */ = { 480 | isa = XCConfigurationList; 481 | buildConfigurations = ( 482 | EDBC8CEBD2AFC4A7AAD607967C2D61B9 /* Debug */, 483 | 8767D2E96CD99B0C6ACD2F35D6AB9988 /* Release */, 484 | ); 485 | defaultConfigurationIsVisible = 0; 486 | defaultConfigurationName = Release; 487 | }; 488 | 4821239608C13582E20E6DA73FD5F1F9 /* Build configuration list for PBXProject "Pods" */ = { 489 | isa = XCConfigurationList; 490 | buildConfigurations = ( 491 | 7EF7227D9B20A1D549000096ACCB23D7 /* Debug */, 492 | 4BE66A09A74FD25164AAB3C2645B9B93 /* Release */, 493 | ); 494 | defaultConfigurationIsVisible = 0; 495 | defaultConfigurationName = Release; 496 | }; 497 | BF535641E00BECC6FFAF53CFB25A8755 /* Build configuration list for PBXNativeTarget "CocoaAsyncSocket" */ = { 498 | isa = XCConfigurationList; 499 | buildConfigurations = ( 500 | 2BAB697BF6B09E8232C79E9481F78A70 /* Debug */, 501 | 9A3244A0C1ED230D9CAF416848B3DAA9 /* Release */, 502 | ); 503 | defaultConfigurationIsVisible = 0; 504 | defaultConfigurationName = Release; 505 | }; 506 | /* End XCConfigurationList section */ 507 | }; 508 | rootObject = BFDFE7DC352907FC980B868725387E98 /* Project object */; 509 | } 510 | -------------------------------------------------------------------------------- /Pods/CocoaAsyncSocket/Source/GCD/GCDAsyncUdpSocket.h: -------------------------------------------------------------------------------- 1 | // 2 | // GCDAsyncUdpSocket 3 | // 4 | // This class is in the public domain. 5 | // Originally created by Robbie Hanson of Deusty LLC. 6 | // Updated and maintained by Deusty LLC and the Apple development community. 7 | // 8 | // https://github.com/robbiehanson/CocoaAsyncSocket 9 | // 10 | 11 | #import 12 | #import 13 | #import 14 | #import 15 | 16 | NS_ASSUME_NONNULL_BEGIN 17 | extern NSString *const GCDAsyncUdpSocketException; 18 | extern NSString *const GCDAsyncUdpSocketErrorDomain; 19 | 20 | extern NSString *const GCDAsyncUdpSocketQueueName; 21 | extern NSString *const GCDAsyncUdpSocketThreadName; 22 | 23 | typedef NS_ENUM(NSInteger, GCDAsyncUdpSocketError) { 24 | GCDAsyncUdpSocketNoError = 0, // Never used 25 | GCDAsyncUdpSocketBadConfigError, // Invalid configuration 26 | GCDAsyncUdpSocketBadParamError, // Invalid parameter was passed 27 | GCDAsyncUdpSocketSendTimeoutError, // A send operation timed out 28 | GCDAsyncUdpSocketClosedError, // The socket was closed 29 | GCDAsyncUdpSocketOtherError, // Description provided in userInfo 30 | }; 31 | 32 | //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 33 | #pragma mark - 34 | //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 35 | 36 | @class GCDAsyncUdpSocket; 37 | 38 | @protocol GCDAsyncUdpSocketDelegate 39 | @optional 40 | 41 | /** 42 | * By design, UDP is a connectionless protocol, and connecting is not needed. 43 | * However, you may optionally choose to connect to a particular host for reasons 44 | * outlined in the documentation for the various connect methods listed above. 45 | * 46 | * This method is called if one of the connect methods are invoked, and the connection is successful. 47 | **/ 48 | - (void)udpSocket:(GCDAsyncUdpSocket *)sock didConnectToAddress:(NSData *)address; 49 | 50 | /** 51 | * By design, UDP is a connectionless protocol, and connecting is not needed. 52 | * However, you may optionally choose to connect to a particular host for reasons 53 | * outlined in the documentation for the various connect methods listed above. 54 | * 55 | * This method is called if one of the connect methods are invoked, and the connection fails. 56 | * This may happen, for example, if a domain name is given for the host and the domain name is unable to be resolved. 57 | **/ 58 | - (void)udpSocket:(GCDAsyncUdpSocket *)sock didNotConnect:(NSError * _Nullable)error; 59 | 60 | /** 61 | * Called when the datagram with the given tag has been sent. 62 | **/ 63 | - (void)udpSocket:(GCDAsyncUdpSocket *)sock didSendDataWithTag:(long)tag; 64 | 65 | /** 66 | * Called if an error occurs while trying to send a datagram. 67 | * This could be due to a timeout, or something more serious such as the data being too large to fit in a sigle packet. 68 | **/ 69 | - (void)udpSocket:(GCDAsyncUdpSocket *)sock didNotSendDataWithTag:(long)tag dueToError:(NSError * _Nullable)error; 70 | 71 | /** 72 | * Called when the socket has received the requested datagram. 73 | **/ 74 | - (void)udpSocket:(GCDAsyncUdpSocket *)sock didReceiveData:(NSData *)data 75 | fromAddress:(NSData *)address 76 | withFilterContext:(nullable id)filterContext; 77 | 78 | /** 79 | * Called when the socket is closed. 80 | **/ 81 | - (void)udpSocketDidClose:(GCDAsyncUdpSocket *)sock withError:(NSError * _Nullable)error; 82 | 83 | @end 84 | 85 | /** 86 | * You may optionally set a receive filter for the socket. 87 | * A filter can provide several useful features: 88 | * 89 | * 1. Many times udp packets need to be parsed. 90 | * Since the filter can run in its own independent queue, you can parallelize this parsing quite easily. 91 | * The end result is a parallel socket io, datagram parsing, and packet processing. 92 | * 93 | * 2. Many times udp packets are discarded because they are duplicate/unneeded/unsolicited. 94 | * The filter can prevent such packets from arriving at the delegate. 95 | * And because the filter can run in its own independent queue, this doesn't slow down the delegate. 96 | * 97 | * - Since the udp protocol does not guarantee delivery, udp packets may be lost. 98 | * Many protocols built atop udp thus provide various resend/re-request algorithms. 99 | * This sometimes results in duplicate packets arriving. 100 | * A filter may allow you to architect the duplicate detection code to run in parallel to normal processing. 101 | * 102 | * - Since the udp socket may be connectionless, its possible for unsolicited packets to arrive. 103 | * Such packets need to be ignored. 104 | * 105 | * 3. Sometimes traffic shapers are needed to simulate real world environments. 106 | * A filter allows you to write custom code to simulate such environments. 107 | * The ability to code this yourself is especially helpful when your simulated environment 108 | * is more complicated than simple traffic shaping (e.g. simulating a cone port restricted router), 109 | * or the system tools to handle this aren't available (e.g. on a mobile device). 110 | * 111 | * @param data - The packet that was received. 112 | * @param address - The address the data was received from. 113 | * See utilities section for methods to extract info from address. 114 | * @param context - Out parameter you may optionally set, which will then be passed to the delegate method. 115 | * For example, filter block can parse the data and then, 116 | * pass the parsed data to the delegate. 117 | * 118 | * @returns - YES if the received packet should be passed onto the delegate. 119 | * NO if the received packet should be discarded, and not reported to the delegete. 120 | * 121 | * Example: 122 | * 123 | * GCDAsyncUdpSocketReceiveFilterBlock filter = ^BOOL (NSData *data, NSData *address, id *context) { 124 | * 125 | * MyProtocolMessage *msg = [MyProtocol parseMessage:data]; 126 | * 127 | * *context = response; 128 | * return (response != nil); 129 | * }; 130 | * [udpSocket setReceiveFilter:filter withQueue:myParsingQueue]; 131 | * 132 | **/ 133 | typedef BOOL (^GCDAsyncUdpSocketReceiveFilterBlock)(NSData *data, NSData *address, id __nullable * __nonnull context); 134 | 135 | /** 136 | * You may optionally set a send filter for the socket. 137 | * A filter can provide several interesting possibilities: 138 | * 139 | * 1. Optional caching of resolved addresses for domain names. 140 | * The cache could later be consulted, resulting in fewer system calls to getaddrinfo. 141 | * 142 | * 2. Reusable modules of code for bandwidth monitoring. 143 | * 144 | * 3. Sometimes traffic shapers are needed to simulate real world environments. 145 | * A filter allows you to write custom code to simulate such environments. 146 | * The ability to code this yourself is especially helpful when your simulated environment 147 | * is more complicated than simple traffic shaping (e.g. simulating a cone port restricted router), 148 | * or the system tools to handle this aren't available (e.g. on a mobile device). 149 | * 150 | * @param data - The packet that was received. 151 | * @param address - The address the data was received from. 152 | * See utilities section for methods to extract info from address. 153 | * @param tag - The tag that was passed in the send method. 154 | * 155 | * @returns - YES if the packet should actually be sent over the socket. 156 | * NO if the packet should be silently dropped (not sent over the socket). 157 | * 158 | * Regardless of the return value, the delegate will be informed that the packet was successfully sent. 159 | * 160 | **/ 161 | typedef BOOL (^GCDAsyncUdpSocketSendFilterBlock)(NSData *data, NSData *address, long tag); 162 | 163 | 164 | @interface GCDAsyncUdpSocket : NSObject 165 | 166 | /** 167 | * GCDAsyncUdpSocket uses the standard delegate paradigm, 168 | * but executes all delegate callbacks on a given delegate dispatch queue. 169 | * This allows for maximum concurrency, while at the same time providing easy thread safety. 170 | * 171 | * You MUST set a delegate AND delegate dispatch queue before attempting to 172 | * use the socket, or you will get an error. 173 | * 174 | * The socket queue is optional. 175 | * If you pass NULL, GCDAsyncSocket will automatically create its own socket queue. 176 | * If you choose to provide a socket queue, the socket queue must not be a concurrent queue, 177 | * then please see the discussion for the method markSocketQueueTargetQueue. 178 | * 179 | * The delegate queue and socket queue can optionally be the same. 180 | **/ 181 | - (instancetype)init; 182 | - (instancetype)initWithSocketQueue:(nullable dispatch_queue_t)sq; 183 | - (instancetype)initWithDelegate:(nullable id )aDelegate delegateQueue:(nullable dispatch_queue_t)dq; 184 | - (instancetype)initWithDelegate:(nullable id )aDelegate delegateQueue:(nullable dispatch_queue_t)dq socketQueue:(nullable dispatch_queue_t)sq; 185 | 186 | #pragma mark Configuration 187 | 188 | - (nullable id )delegate; 189 | - (void)setDelegate:(nullable id )delegate; 190 | - (void)synchronouslySetDelegate:(nullable id )delegate; 191 | 192 | - (nullable dispatch_queue_t)delegateQueue; 193 | - (void)setDelegateQueue:(nullable dispatch_queue_t)delegateQueue; 194 | - (void)synchronouslySetDelegateQueue:(nullable dispatch_queue_t)delegateQueue; 195 | 196 | - (void)getDelegate:(id __nullable * __nullable)delegatePtr delegateQueue:(dispatch_queue_t __nullable * __nullable)delegateQueuePtr; 197 | - (void)setDelegate:(nullable id )delegate delegateQueue:(nullable dispatch_queue_t)delegateQueue; 198 | - (void)synchronouslySetDelegate:(nullable id )delegate delegateQueue:(nullable dispatch_queue_t)delegateQueue; 199 | 200 | /** 201 | * By default, both IPv4 and IPv6 are enabled. 202 | * 203 | * This means GCDAsyncUdpSocket automatically supports both protocols, 204 | * and can send to IPv4 or IPv6 addresses, 205 | * as well as receive over IPv4 and IPv6. 206 | * 207 | * For operations that require DNS resolution, GCDAsyncUdpSocket supports both IPv4 and IPv6. 208 | * If a DNS lookup returns only IPv4 results, GCDAsyncUdpSocket will automatically use IPv4. 209 | * If a DNS lookup returns only IPv6 results, GCDAsyncUdpSocket will automatically use IPv6. 210 | * If a DNS lookup returns both IPv4 and IPv6 results, then the protocol used depends on the configured preference. 211 | * If IPv4 is preferred, then IPv4 is used. 212 | * If IPv6 is preferred, then IPv6 is used. 213 | * If neutral, then the first IP version in the resolved array will be used. 214 | * 215 | * Starting with Mac OS X 10.7 Lion and iOS 5, the default IP preference is neutral. 216 | * On prior systems the default IP preference is IPv4. 217 | **/ 218 | - (BOOL)isIPv4Enabled; 219 | - (void)setIPv4Enabled:(BOOL)flag; 220 | 221 | - (BOOL)isIPv6Enabled; 222 | - (void)setIPv6Enabled:(BOOL)flag; 223 | 224 | - (BOOL)isIPv4Preferred; 225 | - (BOOL)isIPv6Preferred; 226 | - (BOOL)isIPVersionNeutral; 227 | 228 | - (void)setPreferIPv4; 229 | - (void)setPreferIPv6; 230 | - (void)setIPVersionNeutral; 231 | 232 | /** 233 | * Gets/Sets the maximum size of the buffer that will be allocated for receive operations. 234 | * The default maximum size is 65535 bytes. 235 | * 236 | * The theoretical maximum size of any IPv4 UDP packet is UINT16_MAX = 65535. 237 | * The theoretical maximum size of any IPv6 UDP packet is UINT32_MAX = 4294967295. 238 | * 239 | * Since the OS/GCD notifies us of the size of each received UDP packet, 240 | * the actual allocated buffer size for each packet is exact. 241 | * And in practice the size of UDP packets is generally much smaller than the max. 242 | * Indeed most protocols will send and receive packets of only a few bytes, 243 | * or will set a limit on the size of packets to prevent fragmentation in the IP layer. 244 | * 245 | * If you set the buffer size too small, the sockets API in the OS will silently discard 246 | * any extra data, and you will not be notified of the error. 247 | **/ 248 | - (uint16_t)maxReceiveIPv4BufferSize; 249 | - (void)setMaxReceiveIPv4BufferSize:(uint16_t)max; 250 | 251 | - (uint32_t)maxReceiveIPv6BufferSize; 252 | - (void)setMaxReceiveIPv6BufferSize:(uint32_t)max; 253 | 254 | /** 255 | * Gets/Sets the maximum size of the buffer that will be allocated for send operations. 256 | * The default maximum size is 65535 bytes. 257 | * 258 | * Given that a typical link MTU is 1500 bytes, a large UDP datagram will have to be 259 | * fragmented, and that’s both expensive and risky (if one fragment goes missing, the 260 | * entire datagram is lost). You are much better off sending a large number of smaller 261 | * UDP datagrams, preferably using a path MTU algorithm to avoid fragmentation. 262 | * 263 | * You must set it before the sockt is created otherwise it won't work. 264 | * 265 | **/ 266 | - (uint16_t)maxSendBufferSize; 267 | - (void)setMaxSendBufferSize:(uint16_t)max; 268 | 269 | /** 270 | * User data allows you to associate arbitrary information with the socket. 271 | * This data is not used internally in any way. 272 | **/ 273 | - (nullable id)userData; 274 | - (void)setUserData:(nullable id)arbitraryUserData; 275 | 276 | #pragma mark Diagnostics 277 | 278 | /** 279 | * Returns the local address info for the socket. 280 | * 281 | * The localAddress method returns a sockaddr structure wrapped in a NSData object. 282 | * The localHost method returns the human readable IP address as a string. 283 | * 284 | * Note: Address info may not be available until after the socket has been binded, connected 285 | * or until after data has been sent. 286 | **/ 287 | - (nullable NSData *)localAddress; 288 | - (nullable NSString *)localHost; 289 | - (uint16_t)localPort; 290 | 291 | - (nullable NSData *)localAddress_IPv4; 292 | - (nullable NSString *)localHost_IPv4; 293 | - (uint16_t)localPort_IPv4; 294 | 295 | - (nullable NSData *)localAddress_IPv6; 296 | - (nullable NSString *)localHost_IPv6; 297 | - (uint16_t)localPort_IPv6; 298 | 299 | /** 300 | * Returns the remote address info for the socket. 301 | * 302 | * The connectedAddress method returns a sockaddr structure wrapped in a NSData object. 303 | * The connectedHost method returns the human readable IP address as a string. 304 | * 305 | * Note: Since UDP is connectionless by design, connected address info 306 | * will not be available unless the socket is explicitly connected to a remote host/port. 307 | * If the socket is not connected, these methods will return nil / 0. 308 | **/ 309 | - (nullable NSData *)connectedAddress; 310 | - (nullable NSString *)connectedHost; 311 | - (uint16_t)connectedPort; 312 | 313 | /** 314 | * Returns whether or not this socket has been connected to a single host. 315 | * By design, UDP is a connectionless protocol, and connecting is not needed. 316 | * If connected, the socket will only be able to send/receive data to/from the connected host. 317 | **/ 318 | - (BOOL)isConnected; 319 | 320 | /** 321 | * Returns whether or not this socket has been closed. 322 | * The only way a socket can be closed is if you explicitly call one of the close methods. 323 | **/ 324 | - (BOOL)isClosed; 325 | 326 | /** 327 | * Returns whether or not this socket is IPv4. 328 | * 329 | * By default this will be true, unless: 330 | * - IPv4 is disabled (via setIPv4Enabled:) 331 | * - The socket is explicitly bound to an IPv6 address 332 | * - The socket is connected to an IPv6 address 333 | **/ 334 | - (BOOL)isIPv4; 335 | 336 | /** 337 | * Returns whether or not this socket is IPv6. 338 | * 339 | * By default this will be true, unless: 340 | * - IPv6 is disabled (via setIPv6Enabled:) 341 | * - The socket is explicitly bound to an IPv4 address 342 | * _ The socket is connected to an IPv4 address 343 | * 344 | * This method will also return false on platforms that do not support IPv6. 345 | * Note: The iPhone does not currently support IPv6. 346 | **/ 347 | - (BOOL)isIPv6; 348 | 349 | #pragma mark Binding 350 | 351 | /** 352 | * Binds the UDP socket to the given port. 353 | * Binding should be done for server sockets that receive data prior to sending it. 354 | * Client sockets can skip binding, 355 | * as the OS will automatically assign the socket an available port when it starts sending data. 356 | * 357 | * You may optionally pass a port number of zero to immediately bind the socket, 358 | * yet still allow the OS to automatically assign an available port. 359 | * 360 | * You cannot bind a socket after its been connected. 361 | * You can only bind a socket once. 362 | * You can still connect a socket (if desired) after binding. 363 | * 364 | * On success, returns YES. 365 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass NULL for errPtr. 366 | **/ 367 | - (BOOL)bindToPort:(uint16_t)port error:(NSError **)errPtr; 368 | 369 | /** 370 | * Binds the UDP socket to the given port and optional interface. 371 | * Binding should be done for server sockets that receive data prior to sending it. 372 | * Client sockets can skip binding, 373 | * as the OS will automatically assign the socket an available port when it starts sending data. 374 | * 375 | * You may optionally pass a port number of zero to immediately bind the socket, 376 | * yet still allow the OS to automatically assign an available port. 377 | * 378 | * The interface may be a name (e.g. "en1" or "lo0") or the corresponding IP address (e.g. "192.168.4.35"). 379 | * You may also use the special strings "localhost" or "loopback" to specify that 380 | * the socket only accept packets from the local machine. 381 | * 382 | * You cannot bind a socket after its been connected. 383 | * You can only bind a socket once. 384 | * You can still connect a socket (if desired) after binding. 385 | * 386 | * On success, returns YES. 387 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass NULL for errPtr. 388 | **/ 389 | - (BOOL)bindToPort:(uint16_t)port interface:(nullable NSString *)interface error:(NSError **)errPtr; 390 | 391 | /** 392 | * Binds the UDP socket to the given address, specified as a sockaddr structure wrapped in a NSData object. 393 | * 394 | * If you have an existing struct sockaddr you can convert it to a NSData object like so: 395 | * struct sockaddr sa -> NSData *dsa = [NSData dataWithBytes:&remoteAddr length:remoteAddr.sa_len]; 396 | * struct sockaddr *sa -> NSData *dsa = [NSData dataWithBytes:remoteAddr length:remoteAddr->sa_len]; 397 | * 398 | * Binding should be done for server sockets that receive data prior to sending it. 399 | * Client sockets can skip binding, 400 | * as the OS will automatically assign the socket an available port when it starts sending data. 401 | * 402 | * You cannot bind a socket after its been connected. 403 | * You can only bind a socket once. 404 | * You can still connect a socket (if desired) after binding. 405 | * 406 | * On success, returns YES. 407 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass NULL for errPtr. 408 | **/ 409 | - (BOOL)bindToAddress:(NSData *)localAddr error:(NSError **)errPtr; 410 | 411 | #pragma mark Connecting 412 | 413 | /** 414 | * Connects the UDP socket to the given host and port. 415 | * By design, UDP is a connectionless protocol, and connecting is not needed. 416 | * 417 | * Choosing to connect to a specific host/port has the following effect: 418 | * - You will only be able to send data to the connected host/port. 419 | * - You will only be able to receive data from the connected host/port. 420 | * - You will receive ICMP messages that come from the connected host/port, such as "connection refused". 421 | * 422 | * The actual process of connecting a UDP socket does not result in any communication on the socket. 423 | * It simply changes the internal state of the socket. 424 | * 425 | * You cannot bind a socket after it has been connected. 426 | * You can only connect a socket once. 427 | * 428 | * The host may be a domain name (e.g. "deusty.com") or an IP address string (e.g. "192.168.0.2"). 429 | * 430 | * This method is asynchronous as it requires a DNS lookup to resolve the given host name. 431 | * If an obvious error is detected, this method immediately returns NO and sets errPtr. 432 | * If you don't care about the error, you can pass nil for errPtr. 433 | * Otherwise, this method returns YES and begins the asynchronous connection process. 434 | * The result of the asynchronous connection process will be reported via the delegate methods. 435 | **/ 436 | - (BOOL)connectToHost:(NSString *)host onPort:(uint16_t)port error:(NSError **)errPtr; 437 | 438 | /** 439 | * Connects the UDP socket to the given address, specified as a sockaddr structure wrapped in a NSData object. 440 | * 441 | * If you have an existing struct sockaddr you can convert it to a NSData object like so: 442 | * struct sockaddr sa -> NSData *dsa = [NSData dataWithBytes:&remoteAddr length:remoteAddr.sa_len]; 443 | * struct sockaddr *sa -> NSData *dsa = [NSData dataWithBytes:remoteAddr length:remoteAddr->sa_len]; 444 | * 445 | * By design, UDP is a connectionless protocol, and connecting is not needed. 446 | * 447 | * Choosing to connect to a specific address has the following effect: 448 | * - You will only be able to send data to the connected address. 449 | * - You will only be able to receive data from the connected address. 450 | * - You will receive ICMP messages that come from the connected address, such as "connection refused". 451 | * 452 | * Connecting a UDP socket does not result in any communication on the socket. 453 | * It simply changes the internal state of the socket. 454 | * 455 | * You cannot bind a socket after its been connected. 456 | * You can only connect a socket once. 457 | * 458 | * On success, returns YES. 459 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass nil for errPtr. 460 | * 461 | * Note: Unlike the connectToHost:onPort:error: method, this method does not require a DNS lookup. 462 | * Thus when this method returns, the connection has either failed or fully completed. 463 | * In other words, this method is synchronous, unlike the asynchronous connectToHost::: method. 464 | * However, for compatibility and simplification of delegate code, if this method returns YES 465 | * then the corresponding delegate method (udpSocket:didConnectToHost:port:) is still invoked. 466 | **/ 467 | - (BOOL)connectToAddress:(NSData *)remoteAddr error:(NSError **)errPtr; 468 | 469 | #pragma mark Multicast 470 | 471 | /** 472 | * Join multicast group. 473 | * Group should be an IP address (eg @"225.228.0.1"). 474 | * 475 | * On success, returns YES. 476 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass nil for errPtr. 477 | **/ 478 | - (BOOL)joinMulticastGroup:(NSString *)group error:(NSError **)errPtr; 479 | 480 | /** 481 | * Join multicast group. 482 | * Group should be an IP address (eg @"225.228.0.1"). 483 | * The interface may be a name (e.g. "en1" or "lo0") or the corresponding IP address (e.g. "192.168.4.35"). 484 | * 485 | * On success, returns YES. 486 | * Otherwise returns NO, and sets errPtr. If you don't care about the error, you can pass nil for errPtr. 487 | **/ 488 | - (BOOL)joinMulticastGroup:(NSString *)group onInterface:(nullable NSString *)interface error:(NSError **)errPtr; 489 | 490 | - (BOOL)leaveMulticastGroup:(NSString *)group error:(NSError **)errPtr; 491 | - (BOOL)leaveMulticastGroup:(NSString *)group onInterface:(nullable NSString *)interface error:(NSError **)errPtr; 492 | 493 | #pragma mark Reuse Port 494 | 495 | /** 496 | * By default, only one socket can be bound to a given IP address + port at a time. 497 | * To enable multiple processes to simultaneously bind to the same address+port, 498 | * you need to enable this functionality in the socket. All processes that wish to 499 | * use the address+port simultaneously must all enable reuse port on the socket 500 | * bound to that port. 501 | **/ 502 | - (BOOL)enableReusePort:(BOOL)flag error:(NSError **)errPtr; 503 | 504 | #pragma mark Broadcast 505 | 506 | /** 507 | * By default, the underlying socket in the OS will not allow you to send broadcast messages. 508 | * In order to send broadcast messages, you need to enable this functionality in the socket. 509 | * 510 | * A broadcast is a UDP message to addresses like "192.168.255.255" or "255.255.255.255" that is 511 | * delivered to every host on the network. 512 | * The reason this is generally disabled by default (by the OS) is to prevent 513 | * accidental broadcast messages from flooding the network. 514 | **/ 515 | - (BOOL)enableBroadcast:(BOOL)flag error:(NSError **)errPtr; 516 | 517 | #pragma mark Sending 518 | 519 | /** 520 | * Asynchronously sends the given data, with the given timeout and tag. 521 | * 522 | * This method may only be used with a connected socket. 523 | * Recall that connecting is optional for a UDP socket. 524 | * For connected sockets, data can only be sent to the connected address. 525 | * For non-connected sockets, the remote destination is specified for each packet. 526 | * For more information about optionally connecting udp sockets, see the documentation for the connect methods above. 527 | * 528 | * @param data 529 | * The data to send. 530 | * If data is nil or zero-length, this method does nothing. 531 | * If passing NSMutableData, please read the thread-safety notice below. 532 | * 533 | * @param timeout 534 | * The timeout for the send opeartion. 535 | * If the timeout value is negative, the send operation will not use a timeout. 536 | * 537 | * @param tag 538 | * The tag is for your convenience. 539 | * It is not sent or received over the socket in any manner what-so-ever. 540 | * It is reported back as a parameter in the udpSocket:didSendDataWithTag: 541 | * or udpSocket:didNotSendDataWithTag:dueToError: methods. 542 | * You can use it as an array index, state id, type constant, etc. 543 | * 544 | * 545 | * Thread-Safety Note: 546 | * If the given data parameter is mutable (NSMutableData) then you MUST NOT alter the data while 547 | * the socket is sending it. In other words, it's not safe to alter the data until after the delegate method 548 | * udpSocket:didSendDataWithTag: or udpSocket:didNotSendDataWithTag:dueToError: is invoked signifying 549 | * that this particular send operation has completed. 550 | * This is due to the fact that GCDAsyncUdpSocket does NOT copy the data. 551 | * It simply retains it for performance reasons. 552 | * Often times, if NSMutableData is passed, it is because a request/response was built up in memory. 553 | * Copying this data adds an unwanted/unneeded overhead. 554 | * If you need to write data from an immutable buffer, and you need to alter the buffer before the socket 555 | * completes sending the bytes (which is NOT immediately after this method returns, but rather at a later time 556 | * when the delegate method notifies you), then you should first copy the bytes, and pass the copy to this method. 557 | **/ 558 | - (void)sendData:(NSData *)data withTimeout:(NSTimeInterval)timeout tag:(long)tag; 559 | 560 | /** 561 | * Asynchronously sends the given data, with the given timeout and tag, to the given host and port. 562 | * 563 | * This method cannot be used with a connected socket. 564 | * Recall that connecting is optional for a UDP socket. 565 | * For connected sockets, data can only be sent to the connected address. 566 | * For non-connected sockets, the remote destination is specified for each packet. 567 | * For more information about optionally connecting udp sockets, see the documentation for the connect methods above. 568 | * 569 | * @param data 570 | * The data to send. 571 | * If data is nil or zero-length, this method does nothing. 572 | * If passing NSMutableData, please read the thread-safety notice below. 573 | * 574 | * @param host 575 | * The destination to send the udp packet to. 576 | * May be specified as a domain name (e.g. "deusty.com") or an IP address string (e.g. "192.168.0.2"). 577 | * You may also use the convenience strings of "loopback" or "localhost". 578 | * 579 | * @param port 580 | * The port of the host to send to. 581 | * 582 | * @param timeout 583 | * The timeout for the send opeartion. 584 | * If the timeout value is negative, the send operation will not use a timeout. 585 | * 586 | * @param tag 587 | * The tag is for your convenience. 588 | * It is not sent or received over the socket in any manner what-so-ever. 589 | * It is reported back as a parameter in the udpSocket:didSendDataWithTag: 590 | * or udpSocket:didNotSendDataWithTag:dueToError: methods. 591 | * You can use it as an array index, state id, type constant, etc. 592 | * 593 | * 594 | * Thread-Safety Note: 595 | * If the given data parameter is mutable (NSMutableData) then you MUST NOT alter the data while 596 | * the socket is sending it. In other words, it's not safe to alter the data until after the delegate method 597 | * udpSocket:didSendDataWithTag: or udpSocket:didNotSendDataWithTag:dueToError: is invoked signifying 598 | * that this particular send operation has completed. 599 | * This is due to the fact that GCDAsyncUdpSocket does NOT copy the data. 600 | * It simply retains it for performance reasons. 601 | * Often times, if NSMutableData is passed, it is because a request/response was built up in memory. 602 | * Copying this data adds an unwanted/unneeded overhead. 603 | * If you need to write data from an immutable buffer, and you need to alter the buffer before the socket 604 | * completes sending the bytes (which is NOT immediately after this method returns, but rather at a later time 605 | * when the delegate method notifies you), then you should first copy the bytes, and pass the copy to this method. 606 | **/ 607 | - (void)sendData:(NSData *)data 608 | toHost:(NSString *)host 609 | port:(uint16_t)port 610 | withTimeout:(NSTimeInterval)timeout 611 | tag:(long)tag; 612 | 613 | /** 614 | * Asynchronously sends the given data, with the given timeout and tag, to the given address. 615 | * 616 | * This method cannot be used with a connected socket. 617 | * Recall that connecting is optional for a UDP socket. 618 | * For connected sockets, data can only be sent to the connected address. 619 | * For non-connected sockets, the remote destination is specified for each packet. 620 | * For more information about optionally connecting udp sockets, see the documentation for the connect methods above. 621 | * 622 | * @param data 623 | * The data to send. 624 | * If data is nil or zero-length, this method does nothing. 625 | * If passing NSMutableData, please read the thread-safety notice below. 626 | * 627 | * @param remoteAddr 628 | * The address to send the data to (specified as a sockaddr structure wrapped in a NSData object). 629 | * 630 | * @param timeout 631 | * The timeout for the send opeartion. 632 | * If the timeout value is negative, the send operation will not use a timeout. 633 | * 634 | * @param tag 635 | * The tag is for your convenience. 636 | * It is not sent or received over the socket in any manner what-so-ever. 637 | * It is reported back as a parameter in the udpSocket:didSendDataWithTag: 638 | * or udpSocket:didNotSendDataWithTag:dueToError: methods. 639 | * You can use it as an array index, state id, type constant, etc. 640 | * 641 | * 642 | * Thread-Safety Note: 643 | * If the given data parameter is mutable (NSMutableData) then you MUST NOT alter the data while 644 | * the socket is sending it. In other words, it's not safe to alter the data until after the delegate method 645 | * udpSocket:didSendDataWithTag: or udpSocket:didNotSendDataWithTag:dueToError: is invoked signifying 646 | * that this particular send operation has completed. 647 | * This is due to the fact that GCDAsyncUdpSocket does NOT copy the data. 648 | * It simply retains it for performance reasons. 649 | * Often times, if NSMutableData is passed, it is because a request/response was built up in memory. 650 | * Copying this data adds an unwanted/unneeded overhead. 651 | * If you need to write data from an immutable buffer, and you need to alter the buffer before the socket 652 | * completes sending the bytes (which is NOT immediately after this method returns, but rather at a later time 653 | * when the delegate method notifies you), then you should first copy the bytes, and pass the copy to this method. 654 | **/ 655 | - (void)sendData:(NSData *)data toAddress:(NSData *)remoteAddr withTimeout:(NSTimeInterval)timeout tag:(long)tag; 656 | 657 | /** 658 | * You may optionally set a send filter for the socket. 659 | * A filter can provide several interesting possibilities: 660 | * 661 | * 1. Optional caching of resolved addresses for domain names. 662 | * The cache could later be consulted, resulting in fewer system calls to getaddrinfo. 663 | * 664 | * 2. Reusable modules of code for bandwidth monitoring. 665 | * 666 | * 3. Sometimes traffic shapers are needed to simulate real world environments. 667 | * A filter allows you to write custom code to simulate such environments. 668 | * The ability to code this yourself is especially helpful when your simulated environment 669 | * is more complicated than simple traffic shaping (e.g. simulating a cone port restricted router), 670 | * or the system tools to handle this aren't available (e.g. on a mobile device). 671 | * 672 | * For more information about GCDAsyncUdpSocketSendFilterBlock, see the documentation for its typedef. 673 | * To remove a previously set filter, invoke this method and pass a nil filterBlock and NULL filterQueue. 674 | * 675 | * Note: This method invokes setSendFilter:withQueue:isAsynchronous: (documented below), 676 | * passing YES for the isAsynchronous parameter. 677 | **/ 678 | - (void)setSendFilter:(nullable GCDAsyncUdpSocketSendFilterBlock)filterBlock withQueue:(nullable dispatch_queue_t)filterQueue; 679 | 680 | /** 681 | * The receive filter can be run via dispatch_async or dispatch_sync. 682 | * Most typical situations call for asynchronous operation. 683 | * 684 | * However, there are a few situations in which synchronous operation is preferred. 685 | * Such is the case when the filter is extremely minimal and fast. 686 | * This is because dispatch_sync is faster than dispatch_async. 687 | * 688 | * If you choose synchronous operation, be aware of possible deadlock conditions. 689 | * Since the socket queue is executing your block via dispatch_sync, 690 | * then you cannot perform any tasks which may invoke dispatch_sync on the socket queue. 691 | * For example, you can't query properties on the socket. 692 | **/ 693 | - (void)setSendFilter:(nullable GCDAsyncUdpSocketSendFilterBlock)filterBlock 694 | withQueue:(nullable dispatch_queue_t)filterQueue 695 | isAsynchronous:(BOOL)isAsynchronous; 696 | 697 | #pragma mark Receiving 698 | 699 | /** 700 | * There are two modes of operation for receiving packets: one-at-a-time & continuous. 701 | * 702 | * In one-at-a-time mode, you call receiveOnce everytime your delegate is ready to process an incoming udp packet. 703 | * Receiving packets one-at-a-time may be better suited for implementing certain state machine code, 704 | * where your state machine may not always be ready to process incoming packets. 705 | * 706 | * In continuous mode, the delegate is invoked immediately everytime incoming udp packets are received. 707 | * Receiving packets continuously is better suited to real-time streaming applications. 708 | * 709 | * You may switch back and forth between one-at-a-time mode and continuous mode. 710 | * If the socket is currently in continuous mode, calling this method will switch it to one-at-a-time mode. 711 | * 712 | * When a packet is received (and not filtered by the optional receive filter), 713 | * the delegate method (udpSocket:didReceiveData:fromAddress:withFilterContext:) is invoked. 714 | * 715 | * If the socket is able to begin receiving packets, this method returns YES. 716 | * Otherwise it returns NO, and sets the errPtr with appropriate error information. 717 | * 718 | * An example error: 719 | * You created a udp socket to act as a server, and immediately called receive. 720 | * You forgot to first bind the socket to a port number, and received a error with a message like: 721 | * "Must bind socket before you can receive data." 722 | **/ 723 | - (BOOL)receiveOnce:(NSError **)errPtr; 724 | 725 | /** 726 | * There are two modes of operation for receiving packets: one-at-a-time & continuous. 727 | * 728 | * In one-at-a-time mode, you call receiveOnce everytime your delegate is ready to process an incoming udp packet. 729 | * Receiving packets one-at-a-time may be better suited for implementing certain state machine code, 730 | * where your state machine may not always be ready to process incoming packets. 731 | * 732 | * In continuous mode, the delegate is invoked immediately everytime incoming udp packets are received. 733 | * Receiving packets continuously is better suited to real-time streaming applications. 734 | * 735 | * You may switch back and forth between one-at-a-time mode and continuous mode. 736 | * If the socket is currently in one-at-a-time mode, calling this method will switch it to continuous mode. 737 | * 738 | * For every received packet (not filtered by the optional receive filter), 739 | * the delegate method (udpSocket:didReceiveData:fromAddress:withFilterContext:) is invoked. 740 | * 741 | * If the socket is able to begin receiving packets, this method returns YES. 742 | * Otherwise it returns NO, and sets the errPtr with appropriate error information. 743 | * 744 | * An example error: 745 | * You created a udp socket to act as a server, and immediately called receive. 746 | * You forgot to first bind the socket to a port number, and received a error with a message like: 747 | * "Must bind socket before you can receive data." 748 | **/ 749 | - (BOOL)beginReceiving:(NSError **)errPtr; 750 | 751 | /** 752 | * If the socket is currently receiving (beginReceiving has been called), this method pauses the receiving. 753 | * That is, it won't read any more packets from the underlying OS socket until beginReceiving is called again. 754 | * 755 | * Important Note: 756 | * GCDAsyncUdpSocket may be running in parallel with your code. 757 | * That is, your delegate is likely running on a separate thread/dispatch_queue. 758 | * When you invoke this method, GCDAsyncUdpSocket may have already dispatched delegate methods to be invoked. 759 | * Thus, if those delegate methods have already been dispatch_async'd, 760 | * your didReceive delegate method may still be invoked after this method has been called. 761 | * You should be aware of this, and program defensively. 762 | **/ 763 | - (void)pauseReceiving; 764 | 765 | /** 766 | * You may optionally set a receive filter for the socket. 767 | * This receive filter may be set to run in its own queue (independent of delegate queue). 768 | * 769 | * A filter can provide several useful features. 770 | * 771 | * 1. Many times udp packets need to be parsed. 772 | * Since the filter can run in its own independent queue, you can parallelize this parsing quite easily. 773 | * The end result is a parallel socket io, datagram parsing, and packet processing. 774 | * 775 | * 2. Many times udp packets are discarded because they are duplicate/unneeded/unsolicited. 776 | * The filter can prevent such packets from arriving at the delegate. 777 | * And because the filter can run in its own independent queue, this doesn't slow down the delegate. 778 | * 779 | * - Since the udp protocol does not guarantee delivery, udp packets may be lost. 780 | * Many protocols built atop udp thus provide various resend/re-request algorithms. 781 | * This sometimes results in duplicate packets arriving. 782 | * A filter may allow you to architect the duplicate detection code to run in parallel to normal processing. 783 | * 784 | * - Since the udp socket may be connectionless, its possible for unsolicited packets to arrive. 785 | * Such packets need to be ignored. 786 | * 787 | * 3. Sometimes traffic shapers are needed to simulate real world environments. 788 | * A filter allows you to write custom code to simulate such environments. 789 | * The ability to code this yourself is especially helpful when your simulated environment 790 | * is more complicated than simple traffic shaping (e.g. simulating a cone port restricted router), 791 | * or the system tools to handle this aren't available (e.g. on a mobile device). 792 | * 793 | * Example: 794 | * 795 | * GCDAsyncUdpSocketReceiveFilterBlock filter = ^BOOL (NSData *data, NSData *address, id *context) { 796 | * 797 | * MyProtocolMessage *msg = [MyProtocol parseMessage:data]; 798 | * 799 | * *context = response; 800 | * return (response != nil); 801 | * }; 802 | * [udpSocket setReceiveFilter:filter withQueue:myParsingQueue]; 803 | * 804 | * For more information about GCDAsyncUdpSocketReceiveFilterBlock, see the documentation for its typedef. 805 | * To remove a previously set filter, invoke this method and pass a nil filterBlock and NULL filterQueue. 806 | * 807 | * Note: This method invokes setReceiveFilter:withQueue:isAsynchronous: (documented below), 808 | * passing YES for the isAsynchronous parameter. 809 | **/ 810 | - (void)setReceiveFilter:(nullable GCDAsyncUdpSocketReceiveFilterBlock)filterBlock withQueue:(nullable dispatch_queue_t)filterQueue; 811 | 812 | /** 813 | * The receive filter can be run via dispatch_async or dispatch_sync. 814 | * Most typical situations call for asynchronous operation. 815 | * 816 | * However, there are a few situations in which synchronous operation is preferred. 817 | * Such is the case when the filter is extremely minimal and fast. 818 | * This is because dispatch_sync is faster than dispatch_async. 819 | * 820 | * If you choose synchronous operation, be aware of possible deadlock conditions. 821 | * Since the socket queue is executing your block via dispatch_sync, 822 | * then you cannot perform any tasks which may invoke dispatch_sync on the socket queue. 823 | * For example, you can't query properties on the socket. 824 | **/ 825 | - (void)setReceiveFilter:(nullable GCDAsyncUdpSocketReceiveFilterBlock)filterBlock 826 | withQueue:(nullable dispatch_queue_t)filterQueue 827 | isAsynchronous:(BOOL)isAsynchronous; 828 | 829 | #pragma mark Closing 830 | 831 | /** 832 | * Immediately closes the underlying socket. 833 | * Any pending send operations are discarded. 834 | * 835 | * The GCDAsyncUdpSocket instance may optionally be used again. 836 | * (it will setup/configure/use another unnderlying BSD socket). 837 | **/ 838 | - (void)close; 839 | 840 | /** 841 | * Closes the underlying socket after all pending send operations have been sent. 842 | * 843 | * The GCDAsyncUdpSocket instance may optionally be used again. 844 | * (it will setup/configure/use another unnderlying BSD socket). 845 | **/ 846 | - (void)closeAfterSending; 847 | 848 | #pragma mark Advanced 849 | /** 850 | * GCDAsyncSocket maintains thread safety by using an internal serial dispatch_queue. 851 | * In most cases, the instance creates this queue itself. 852 | * However, to allow for maximum flexibility, the internal queue may be passed in the init method. 853 | * This allows for some advanced options such as controlling socket priority via target queues. 854 | * However, when one begins to use target queues like this, they open the door to some specific deadlock issues. 855 | * 856 | * For example, imagine there are 2 queues: 857 | * dispatch_queue_t socketQueue; 858 | * dispatch_queue_t socketTargetQueue; 859 | * 860 | * If you do this (pseudo-code): 861 | * socketQueue.targetQueue = socketTargetQueue; 862 | * 863 | * Then all socketQueue operations will actually get run on the given socketTargetQueue. 864 | * This is fine and works great in most situations. 865 | * But if you run code directly from within the socketTargetQueue that accesses the socket, 866 | * you could potentially get deadlock. Imagine the following code: 867 | * 868 | * - (BOOL)socketHasSomething 869 | * { 870 | * __block BOOL result = NO; 871 | * dispatch_block_t block = ^{ 872 | * result = [self someInternalMethodToBeRunOnlyOnSocketQueue]; 873 | * } 874 | * if (is_executing_on_queue(socketQueue)) 875 | * block(); 876 | * else 877 | * dispatch_sync(socketQueue, block); 878 | * 879 | * return result; 880 | * } 881 | * 882 | * What happens if you call this method from the socketTargetQueue? The result is deadlock. 883 | * This is because the GCD API offers no mechanism to discover a queue's targetQueue. 884 | * Thus we have no idea if our socketQueue is configured with a targetQueue. 885 | * If we had this information, we could easily avoid deadlock. 886 | * But, since these API's are missing or unfeasible, you'll have to explicitly set it. 887 | * 888 | * IF you pass a socketQueue via the init method, 889 | * AND you've configured the passed socketQueue with a targetQueue, 890 | * THEN you should pass the end queue in the target hierarchy. 891 | * 892 | * For example, consider the following queue hierarchy: 893 | * socketQueue -> ipQueue -> moduleQueue 894 | * 895 | * This example demonstrates priority shaping within some server. 896 | * All incoming client connections from the same IP address are executed on the same target queue. 897 | * And all connections for a particular module are executed on the same target queue. 898 | * Thus, the priority of all networking for the entire module can be changed on the fly. 899 | * Additionally, networking traffic from a single IP cannot monopolize the module. 900 | * 901 | * Here's how you would accomplish something like that: 902 | * - (dispatch_queue_t)newSocketQueueForConnectionFromAddress:(NSData *)address onSocket:(GCDAsyncSocket *)sock 903 | * { 904 | * dispatch_queue_t socketQueue = dispatch_queue_create("", NULL); 905 | * dispatch_queue_t ipQueue = [self ipQueueForAddress:address]; 906 | * 907 | * dispatch_set_target_queue(socketQueue, ipQueue); 908 | * dispatch_set_target_queue(iqQueue, moduleQueue); 909 | * 910 | * return socketQueue; 911 | * } 912 | * - (void)socket:(GCDAsyncSocket *)sock didAcceptNewSocket:(GCDAsyncSocket *)newSocket 913 | * { 914 | * [clientConnections addObject:newSocket]; 915 | * [newSocket markSocketQueueTargetQueue:moduleQueue]; 916 | * } 917 | * 918 | * Note: This workaround is ONLY needed if you intend to execute code directly on the ipQueue or moduleQueue. 919 | * This is often NOT the case, as such queues are used solely for execution shaping. 920 | **/ 921 | - (void)markSocketQueueTargetQueue:(dispatch_queue_t)socketQueuesPreConfiguredTargetQueue; 922 | - (void)unmarkSocketQueueTargetQueue:(dispatch_queue_t)socketQueuesPreviouslyConfiguredTargetQueue; 923 | 924 | /** 925 | * It's not thread-safe to access certain variables from outside the socket's internal queue. 926 | * 927 | * For example, the socket file descriptor. 928 | * File descriptors are simply integers which reference an index in the per-process file table. 929 | * However, when one requests a new file descriptor (by opening a file or socket), 930 | * the file descriptor returned is guaranteed to be the lowest numbered unused descriptor. 931 | * So if we're not careful, the following could be possible: 932 | * 933 | * - Thread A invokes a method which returns the socket's file descriptor. 934 | * - The socket is closed via the socket's internal queue on thread B. 935 | * - Thread C opens a file, and subsequently receives the file descriptor that was previously the socket's FD. 936 | * - Thread A is now accessing/altering the file instead of the socket. 937 | * 938 | * In addition to this, other variables are not actually objects, 939 | * and thus cannot be retained/released or even autoreleased. 940 | * An example is the sslContext, of type SSLContextRef, which is actually a malloc'd struct. 941 | * 942 | * Although there are internal variables that make it difficult to maintain thread-safety, 943 | * it is important to provide access to these variables 944 | * to ensure this class can be used in a wide array of environments. 945 | * This method helps to accomplish this by invoking the current block on the socket's internal queue. 946 | * The methods below can be invoked from within the block to access 947 | * those generally thread-unsafe internal variables in a thread-safe manner. 948 | * The given block will be invoked synchronously on the socket's internal queue. 949 | * 950 | * If you save references to any protected variables and use them outside the block, you do so at your own peril. 951 | **/ 952 | - (void)performBlock:(dispatch_block_t)block; 953 | 954 | /** 955 | * These methods are only available from within the context of a performBlock: invocation. 956 | * See the documentation for the performBlock: method above. 957 | * 958 | * Provides access to the socket's file descriptor(s). 959 | * If the socket isn't connected, or explicity bound to a particular interface, 960 | * it might actually have multiple internal socket file descriptors - one for IPv4 and one for IPv6. 961 | **/ 962 | - (int)socketFD; 963 | - (int)socket4FD; 964 | - (int)socket6FD; 965 | 966 | #if TARGET_OS_IPHONE 967 | 968 | /** 969 | * These methods are only available from within the context of a performBlock: invocation. 970 | * See the documentation for the performBlock: method above. 971 | * 972 | * Returns (creating if necessary) a CFReadStream/CFWriteStream for the internal socket. 973 | * 974 | * Generally GCDAsyncUdpSocket doesn't use CFStream. (It uses the faster GCD API's.) 975 | * However, if you need one for any reason, 976 | * these methods are a convenient way to get access to a safe instance of one. 977 | **/ 978 | - (nullable CFReadStreamRef)readStream; 979 | - (nullable CFWriteStreamRef)writeStream; 980 | 981 | /** 982 | * This method is only available from within the context of a performBlock: invocation. 983 | * See the documentation for the performBlock: method above. 984 | * 985 | * Configures the socket to allow it to operate when the iOS application has been backgrounded. 986 | * In other words, this method creates a read & write stream, and invokes: 987 | * 988 | * CFReadStreamSetProperty(readStream, kCFStreamNetworkServiceType, kCFStreamNetworkServiceTypeVoIP); 989 | * CFWriteStreamSetProperty(writeStream, kCFStreamNetworkServiceType, kCFStreamNetworkServiceTypeVoIP); 990 | * 991 | * Returns YES if successful, NO otherwise. 992 | * 993 | * Example usage: 994 | * 995 | * [asyncUdpSocket performBlock:^{ 996 | * [asyncUdpSocket enableBackgroundingOnSocket]; 997 | * }]; 998 | * 999 | * 1000 | * NOTE : Apple doesn't currently support backgrounding UDP sockets. (Only TCP for now). 1001 | **/ 1002 | //- (BOOL)enableBackgroundingOnSockets; 1003 | 1004 | #endif 1005 | 1006 | #pragma mark Utilities 1007 | 1008 | /** 1009 | * Extracting host/port/family information from raw address data. 1010 | **/ 1011 | 1012 | + (nullable NSString *)hostFromAddress:(NSData *)address; 1013 | + (uint16_t)portFromAddress:(NSData *)address; 1014 | + (int)familyFromAddress:(NSData *)address; 1015 | 1016 | + (BOOL)isIPv4Address:(NSData *)address; 1017 | + (BOOL)isIPv6Address:(NSData *)address; 1018 | 1019 | + (BOOL)getHost:(NSString * __nullable * __nullable)hostPtr port:(uint16_t * __nullable)portPtr fromAddress:(NSData *)address; 1020 | + (BOOL)getHost:(NSString * __nullable * __nullable)hostPtr port:(uint16_t * __nullable)portPtr family:(int * __nullable)afPtr fromAddress:(NSData *)address; 1021 | 1022 | @end 1023 | 1024 | NS_ASSUME_NONNULL_END 1025 | --------------------------------------------------------------------------------