├── .gitignore ├── App Resources ├── Assets.xcassets │ ├── AppIcon.appiconset │ │ └── Contents.json │ └── Contents.json ├── Base.lproj │ └── LaunchScreen.storyboard └── Info.plist ├── External └── include │ └── mach │ └── mach_vm_private.h ├── Package └── DEBIAN │ └── control ├── Readme.md ├── Scripts └── build.sh ├── Source ├── Binary Reading │ ├── BinaryError.swift │ ├── DataConvertible.swift │ └── DataView.swift ├── Bridging.h ├── C API Wrappers │ ├── FLXPrivateApi.h │ ├── FLXPrivateApi.mm │ ├── FLXSystemApi.h │ └── FLXSystemApi.m ├── Commands │ ├── DecryptFile.swift │ └── FlexDecrypt.swift ├── Debugging │ └── FLXLog.swift ├── Extensions │ └── Int+Convenience.swift ├── Mach-O │ ├── Decrypt │ │ ├── MachOFile+Decrypt.swift │ │ └── MachOFile+SpawnDecrypt.swift │ ├── MachOBinary.swift │ ├── MachOError.swift │ ├── MachOFile.swift │ ├── MachOSlice.swift │ └── Structure │ │ ├── ArchitectureValue.swift │ │ ├── MachOEncryptionInfo.swift │ │ ├── MachOHeader+DataConvertible.swift │ │ ├── MachOHeader.swift │ │ ├── MachOLoadCommand.swift │ │ ├── MachOSegment.swift │ │ └── MachOStructs.swift ├── flexdecrypt.entitlements └── main.swift └── flexdecrypt.xcodeproj ├── project.pbxproj ├── project.xcworkspace ├── contents.xcworkspacedata └── xcshareddata │ └── IDEWorkspaceChecks.plist └── xcshareddata └── xcschemes └── flexdecrypt.xcscheme /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | *.xccheckout 3 | 4 | ## Build generated 5 | build/ 6 | DerivedData/ 7 | 8 | ## Various settings 9 | *.pbxuser 10 | !default.pbxuser 11 | *.mode1v3 12 | !default.mode1v3 13 | *.mode2v3 14 | !default.mode2v3 15 | *.perspectivev3 16 | !default.perspectivev3 17 | xcuserdata/ 18 | 19 | ## Other 20 | *.moved-aside 21 | *.xcuserstate 22 | 23 | ## Obj-C/Swift specific 24 | *.hmap 25 | *.ipa 26 | *.dSYM.zip 27 | *.dSYM 28 | 29 | ## Playgrounds 30 | timeline.xctimeline 31 | playground.xcworkspace 32 | 33 | # Swift Package Manager 34 | # 35 | # Add this line if you want to avoid checking in source code from Swift Package Manager dependencies. 36 | # Packages/ 37 | .build/ 38 | Package.resolved 39 | Rogue.xcodeproj 40 | 41 | # CocoaPods 42 | # 43 | # We recommend against adding the Pods directory to your .gitignore. However 44 | # you should judge for yourself, the pros and cons are mentioned at: 45 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control 46 | # 47 | Pods/ 48 | 49 | # Carthage 50 | # 51 | # Add this line if you want to avoid checking in source code from Carthage dependencies. 52 | Carthage/Checkouts 53 | Carthage/Build 54 | 55 | # fastlane 56 | # 57 | # It is recommended to not store the screenshots in the git repo. Instead, use fastlane to re-generate the 58 | # screenshots whenever they are needed. 59 | # For more information about the recommended setup visit: 60 | # https://github.com/fastlane/fastlane/blob/master/fastlane/docs/Gitignore.md 61 | fastlane/report.xml 62 | fastlane/Preview.html 63 | fastlane/screenshots 64 | fastlane/test_output 65 | 66 | # Codesigning 67 | *.mobileprovision 68 | *.cer 69 | 70 | ## flexdecrypt 71 | 72 | # Build Generated 73 | /Package/usr/bin/flexdecrypt 74 | /flexdecrypt.deb -------------------------------------------------------------------------------- /App Resources/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "scale" : "2x", 6 | "size" : "20x20" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "scale" : "3x", 11 | "size" : "20x20" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "scale" : "2x", 16 | "size" : "29x29" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "scale" : "3x", 21 | "size" : "29x29" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "scale" : "2x", 26 | "size" : "40x40" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "scale" : "3x", 31 | "size" : "40x40" 32 | }, 33 | { 34 | "idiom" : "iphone", 35 | "scale" : "2x", 36 | "size" : "60x60" 37 | }, 38 | { 39 | "idiom" : "iphone", 40 | "scale" : "3x", 41 | "size" : "60x60" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "scale" : "1x", 46 | "size" : "20x20" 47 | }, 48 | { 49 | "idiom" : "ipad", 50 | "scale" : "2x", 51 | "size" : "20x20" 52 | }, 53 | { 54 | "idiom" : "ipad", 55 | "scale" : "1x", 56 | "size" : "29x29" 57 | }, 58 | { 59 | "idiom" : "ipad", 60 | "scale" : "2x", 61 | "size" : "29x29" 62 | }, 63 | { 64 | "idiom" : "ipad", 65 | "scale" : "1x", 66 | "size" : "40x40" 67 | }, 68 | { 69 | "idiom" : "ipad", 70 | "scale" : "2x", 71 | "size" : "40x40" 72 | }, 73 | { 74 | "idiom" : "ipad", 75 | "scale" : "1x", 76 | "size" : "76x76" 77 | }, 78 | { 79 | "idiom" : "ipad", 80 | "scale" : "2x", 81 | "size" : "76x76" 82 | }, 83 | { 84 | "idiom" : "ipad", 85 | "scale" : "2x", 86 | "size" : "83.5x83.5" 87 | }, 88 | { 89 | "idiom" : "ios-marketing", 90 | "scale" : "1x", 91 | "size" : "1024x1024" 92 | } 93 | ], 94 | "info" : { 95 | "author" : "xcode", 96 | "version" : 1 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /App Resources/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "author" : "xcode", 4 | "version" : 1 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /App Resources/Base.lproj/LaunchScreen.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 | -------------------------------------------------------------------------------- /App Resources/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | $(PRODUCT_BUNDLE_PACKAGE_TYPE) 17 | CFBundleShortVersionString 18 | $(MARKETING_VERSION) 19 | CFBundleVersion 20 | 1 21 | LSRequiresIPhoneOS 22 | 23 | UIApplicationSceneManifest 24 | 25 | UIApplicationSupportsMultipleScenes 26 | 27 | UISceneConfigurations 28 | 29 | UIWindowSceneSessionRoleApplication 30 | 31 | 32 | UISceneConfigurationName 33 | Default Configuration 34 | UISceneDelegateClassName 35 | $(PRODUCT_MODULE_NAME).SceneDelegate 36 | UISceneStoryboardFile 37 | Main 38 | 39 | 40 | 41 | 42 | UILaunchStoryboardName 43 | LaunchScreen 44 | UIRequiredDeviceCapabilities 45 | 46 | armv7 47 | 48 | UISupportedInterfaceOrientations 49 | 50 | UIInterfaceOrientationPortrait 51 | UIInterfaceOrientationLandscapeLeft 52 | UIInterfaceOrientationLandscapeRight 53 | 54 | UISupportedInterfaceOrientations~ipad 55 | 56 | UIInterfaceOrientationPortrait 57 | UIInterfaceOrientationPortraitUpsideDown 58 | UIInterfaceOrientationLandscapeLeft 59 | UIInterfaceOrientationLandscapeRight 60 | 61 | 62 | 63 | -------------------------------------------------------------------------------- /External/include/mach/mach_vm_private.h: -------------------------------------------------------------------------------- 1 | #ifndef _mach_vm_user_ 2 | #define _mach_vm_user_ 3 | 4 | /* Module mach_vm */ 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | 16 | /* BEGIN MIG_STRNCPY_ZEROFILL CODE */ 17 | 18 | #if defined(__has_include) 19 | #if __has_include() 20 | #ifndef USING_MIG_STRNCPY_ZEROFILL 21 | #define USING_MIG_STRNCPY_ZEROFILL 22 | #endif 23 | #ifndef __MIG_STRNCPY_ZEROFILL_FORWARD_TYPE_DECLS__ 24 | #define __MIG_STRNCPY_ZEROFILL_FORWARD_TYPE_DECLS__ 25 | #ifdef __cplusplus 26 | extern "C" { 27 | #endif 28 | extern int mig_strncpy_zerofill(char *dest, const char *src, int len) __attribute__((weak_import)); 29 | #ifdef __cplusplus 30 | } 31 | #endif 32 | #endif /* __MIG_STRNCPY_ZEROFILL_FORWARD_TYPE_DECLS__ */ 33 | #endif /* __has_include() */ 34 | #endif /* __has_include */ 35 | 36 | /* END MIG_STRNCPY_ZEROFILL CODE */ 37 | 38 | 39 | #ifdef AUTOTEST 40 | #ifndef FUNCTION_PTR_T 41 | #define FUNCTION_PTR_T 42 | typedef void (*function_ptr_t)(mach_port_t, char *, mach_msg_type_number_t); 43 | typedef struct { 44 | char *name; 45 | function_ptr_t function; 46 | } function_table_entry; 47 | typedef function_table_entry *function_table_t; 48 | #endif /* FUNCTION_PTR_T */ 49 | #endif /* AUTOTEST */ 50 | 51 | #ifndef mach_vm_MSG_COUNT 52 | #define mach_vm_MSG_COUNT 21 53 | #endif /* mach_vm_MSG_COUNT */ 54 | 55 | #include 56 | #include 57 | #include 58 | #include 59 | #include 60 | 61 | #ifdef __BeforeMigUserHeader 62 | __BeforeMigUserHeader 63 | #endif /* __BeforeMigUserHeader */ 64 | 65 | #include 66 | __BEGIN_DECLS 67 | 68 | 69 | /* Routine mach_vm_allocate */ 70 | #ifdef mig_external 71 | mig_external 72 | #else 73 | extern 74 | #endif /* mig_external */ 75 | kern_return_t mach_vm_allocate 76 | ( 77 | vm_map_t target, 78 | mach_vm_address_t *address, 79 | mach_vm_size_t size, 80 | int flags 81 | ); 82 | 83 | /* Routine mach_vm_deallocate */ 84 | #ifdef mig_external 85 | mig_external 86 | #else 87 | extern 88 | #endif /* mig_external */ 89 | kern_return_t mach_vm_deallocate 90 | ( 91 | vm_map_t target, 92 | mach_vm_address_t address, 93 | mach_vm_size_t size 94 | ); 95 | 96 | /* Routine mach_vm_protect */ 97 | #ifdef mig_external 98 | mig_external 99 | #else 100 | extern 101 | #endif /* mig_external */ 102 | kern_return_t mach_vm_protect 103 | ( 104 | vm_map_t target_task, 105 | mach_vm_address_t address, 106 | mach_vm_size_t size, 107 | boolean_t set_maximum, 108 | vm_prot_t new_protection 109 | ); 110 | 111 | /* Routine mach_vm_inherit */ 112 | #ifdef mig_external 113 | mig_external 114 | #else 115 | extern 116 | #endif /* mig_external */ 117 | kern_return_t mach_vm_inherit 118 | ( 119 | vm_map_t target_task, 120 | mach_vm_address_t address, 121 | mach_vm_size_t size, 122 | vm_inherit_t new_inheritance 123 | ); 124 | 125 | /* Routine mach_vm_read */ 126 | #ifdef mig_external 127 | mig_external 128 | #else 129 | extern 130 | #endif /* mig_external */ 131 | kern_return_t mach_vm_read 132 | ( 133 | vm_map_t target_task, 134 | mach_vm_address_t address, 135 | mach_vm_size_t size, 136 | vm_offset_t *data, 137 | mach_msg_type_number_t *dataCnt 138 | ); 139 | 140 | /* Routine mach_vm_read_list */ 141 | #ifdef mig_external 142 | mig_external 143 | #else 144 | extern 145 | #endif /* mig_external */ 146 | kern_return_t mach_vm_read_list 147 | ( 148 | vm_map_t target_task, 149 | mach_vm_read_entry_t data_list, 150 | natural_t count 151 | ); 152 | 153 | /* Routine mach_vm_write */ 154 | #ifdef mig_external 155 | mig_external 156 | #else 157 | extern 158 | #endif /* mig_external */ 159 | kern_return_t mach_vm_write 160 | ( 161 | vm_map_t target_task, 162 | mach_vm_address_t address, 163 | vm_offset_t data, 164 | mach_msg_type_number_t dataCnt 165 | ); 166 | 167 | /* Routine mach_vm_copy */ 168 | #ifdef mig_external 169 | mig_external 170 | #else 171 | extern 172 | #endif /* mig_external */ 173 | kern_return_t mach_vm_copy 174 | ( 175 | vm_map_t target_task, 176 | mach_vm_address_t source_address, 177 | mach_vm_size_t size, 178 | mach_vm_address_t dest_address 179 | ); 180 | 181 | /* Routine mach_vm_read_overwrite */ 182 | #ifdef mig_external 183 | mig_external 184 | #else 185 | extern 186 | #endif /* mig_external */ 187 | kern_return_t mach_vm_read_overwrite 188 | ( 189 | vm_map_t target_task, 190 | mach_vm_address_t address, 191 | mach_vm_size_t size, 192 | mach_vm_address_t data, 193 | mach_vm_size_t *outsize 194 | ); 195 | 196 | /* Routine mach_vm_msync */ 197 | #ifdef mig_external 198 | mig_external 199 | #else 200 | extern 201 | #endif /* mig_external */ 202 | kern_return_t mach_vm_msync 203 | ( 204 | vm_map_t target_task, 205 | mach_vm_address_t address, 206 | mach_vm_size_t size, 207 | vm_sync_t sync_flags 208 | ); 209 | 210 | /* Routine mach_vm_behavior_set */ 211 | #ifdef mig_external 212 | mig_external 213 | #else 214 | extern 215 | #endif /* mig_external */ 216 | kern_return_t mach_vm_behavior_set 217 | ( 218 | vm_map_t target_task, 219 | mach_vm_address_t address, 220 | mach_vm_size_t size, 221 | vm_behavior_t new_behavior 222 | ); 223 | 224 | /* Routine mach_vm_map */ 225 | #ifdef mig_external 226 | mig_external 227 | #else 228 | extern 229 | #endif /* mig_external */ 230 | kern_return_t mach_vm_map 231 | ( 232 | vm_map_t target_task, 233 | mach_vm_address_t *address, 234 | mach_vm_size_t size, 235 | mach_vm_offset_t mask, 236 | int flags, 237 | mem_entry_name_port_t object, 238 | memory_object_offset_t offset, 239 | boolean_t copy, 240 | vm_prot_t cur_protection, 241 | vm_prot_t max_protection, 242 | vm_inherit_t inheritance 243 | ); 244 | 245 | /* Routine mach_vm_machine_attribute */ 246 | #ifdef mig_external 247 | mig_external 248 | #else 249 | extern 250 | #endif /* mig_external */ 251 | kern_return_t mach_vm_machine_attribute 252 | ( 253 | vm_map_t target_task, 254 | mach_vm_address_t address, 255 | mach_vm_size_t size, 256 | vm_machine_attribute_t attribute, 257 | vm_machine_attribute_val_t *value 258 | ); 259 | 260 | /* Routine mach_vm_remap */ 261 | #ifdef mig_external 262 | mig_external 263 | #else 264 | extern 265 | #endif /* mig_external */ 266 | kern_return_t mach_vm_remap 267 | ( 268 | vm_map_t target_task, 269 | mach_vm_address_t *target_address, 270 | mach_vm_size_t size, 271 | mach_vm_offset_t mask, 272 | int flags, 273 | vm_map_t src_task, 274 | mach_vm_address_t src_address, 275 | boolean_t copy, 276 | vm_prot_t *cur_protection, 277 | vm_prot_t *max_protection, 278 | vm_inherit_t inheritance 279 | ); 280 | 281 | /* Routine mach_vm_page_query */ 282 | #ifdef mig_external 283 | mig_external 284 | #else 285 | extern 286 | #endif /* mig_external */ 287 | kern_return_t mach_vm_page_query 288 | ( 289 | vm_map_t target_map, 290 | mach_vm_offset_t offset, 291 | integer_t *disposition, 292 | integer_t *ref_count 293 | ); 294 | 295 | /* Routine mach_vm_region_recurse */ 296 | #ifdef mig_external 297 | mig_external 298 | #else 299 | extern 300 | #endif /* mig_external */ 301 | kern_return_t mach_vm_region_recurse 302 | ( 303 | vm_map_t target_task, 304 | mach_vm_address_t *address, 305 | mach_vm_size_t *size, 306 | natural_t *nesting_depth, 307 | vm_region_recurse_info_t info, 308 | mach_msg_type_number_t *infoCnt 309 | ); 310 | 311 | /* Routine mach_vm_region */ 312 | #ifdef mig_external 313 | mig_external 314 | #else 315 | extern 316 | #endif /* mig_external */ 317 | kern_return_t mach_vm_region 318 | ( 319 | vm_map_t target_task, 320 | mach_vm_address_t *address, 321 | mach_vm_size_t *size, 322 | vm_region_flavor_t flavor, 323 | vm_region_info_t info, 324 | mach_msg_type_number_t *infoCnt, 325 | mach_port_t *object_name 326 | ); 327 | 328 | /* Routine _mach_make_memory_entry */ 329 | #ifdef mig_external 330 | mig_external 331 | #else 332 | extern 333 | #endif /* mig_external */ 334 | kern_return_t _mach_make_memory_entry 335 | ( 336 | vm_map_t target_task, 337 | memory_object_size_t *size, 338 | memory_object_offset_t offset, 339 | vm_prot_t permission, 340 | mem_entry_name_port_t *object_handle, 341 | mem_entry_name_port_t parent_handle 342 | ); 343 | 344 | /* Routine mach_vm_purgable_control */ 345 | #ifdef mig_external 346 | mig_external 347 | #else 348 | extern 349 | #endif /* mig_external */ 350 | kern_return_t mach_vm_purgable_control 351 | ( 352 | vm_map_t target_task, 353 | mach_vm_address_t address, 354 | vm_purgable_t control, 355 | int *state 356 | ); 357 | 358 | /* Routine mach_vm_page_info */ 359 | #ifdef mig_external 360 | mig_external 361 | #else 362 | extern 363 | #endif /* mig_external */ 364 | kern_return_t mach_vm_page_info 365 | ( 366 | vm_map_t target_task, 367 | mach_vm_address_t address, 368 | vm_page_info_flavor_t flavor, 369 | vm_page_info_t info, 370 | mach_msg_type_number_t *infoCnt 371 | ); 372 | 373 | /* Routine mach_vm_page_range_query */ 374 | #ifdef mig_external 375 | mig_external 376 | #else 377 | extern 378 | #endif /* mig_external */ 379 | kern_return_t mach_vm_page_range_query 380 | ( 381 | vm_map_t target_map, 382 | mach_vm_offset_t address, 383 | mach_vm_size_t size, 384 | mach_vm_address_t dispositions, 385 | mach_vm_size_t *dispositions_count 386 | ); 387 | 388 | __END_DECLS 389 | 390 | /********************** Caution **************************/ 391 | /* The following data types should be used to calculate */ 392 | /* maximum message sizes only. The actual message may be */ 393 | /* smaller, and the position of the arguments within the */ 394 | /* message layout may vary from what is presented here. */ 395 | /* For example, if any of the arguments are variable- */ 396 | /* sized, and less than the maximum is sent, the data */ 397 | /* will be packed tight in the actual message to reduce */ 398 | /* the presence of holes. */ 399 | /********************** Caution **************************/ 400 | 401 | /* typedefs for all requests */ 402 | 403 | #ifndef __Request__mach_vm_subsystem__defined 404 | #define __Request__mach_vm_subsystem__defined 405 | 406 | #ifdef __MigPackStructs 407 | #pragma pack(4) 408 | #endif 409 | typedef struct { 410 | mach_msg_header_t Head; 411 | NDR_record_t NDR; 412 | mach_vm_address_t address; 413 | mach_vm_size_t size; 414 | int flags; 415 | } __Request__mach_vm_allocate_t __attribute__((unused)); 416 | #ifdef __MigPackStructs 417 | #pragma pack() 418 | #endif 419 | 420 | #ifdef __MigPackStructs 421 | #pragma pack(4) 422 | #endif 423 | typedef struct { 424 | mach_msg_header_t Head; 425 | NDR_record_t NDR; 426 | mach_vm_address_t address; 427 | mach_vm_size_t size; 428 | } __Request__mach_vm_deallocate_t __attribute__((unused)); 429 | #ifdef __MigPackStructs 430 | #pragma pack() 431 | #endif 432 | 433 | #ifdef __MigPackStructs 434 | #pragma pack(4) 435 | #endif 436 | typedef struct { 437 | mach_msg_header_t Head; 438 | NDR_record_t NDR; 439 | mach_vm_address_t address; 440 | mach_vm_size_t size; 441 | boolean_t set_maximum; 442 | vm_prot_t new_protection; 443 | } __Request__mach_vm_protect_t __attribute__((unused)); 444 | #ifdef __MigPackStructs 445 | #pragma pack() 446 | #endif 447 | 448 | #ifdef __MigPackStructs 449 | #pragma pack(4) 450 | #endif 451 | typedef struct { 452 | mach_msg_header_t Head; 453 | NDR_record_t NDR; 454 | mach_vm_address_t address; 455 | mach_vm_size_t size; 456 | vm_inherit_t new_inheritance; 457 | } __Request__mach_vm_inherit_t __attribute__((unused)); 458 | #ifdef __MigPackStructs 459 | #pragma pack() 460 | #endif 461 | 462 | #ifdef __MigPackStructs 463 | #pragma pack(4) 464 | #endif 465 | typedef struct { 466 | mach_msg_header_t Head; 467 | NDR_record_t NDR; 468 | mach_vm_address_t address; 469 | mach_vm_size_t size; 470 | } __Request__mach_vm_read_t __attribute__((unused)); 471 | #ifdef __MigPackStructs 472 | #pragma pack() 473 | #endif 474 | 475 | #ifdef __MigPackStructs 476 | #pragma pack(4) 477 | #endif 478 | typedef struct { 479 | mach_msg_header_t Head; 480 | NDR_record_t NDR; 481 | mach_vm_read_entry_t data_list; 482 | natural_t count; 483 | } __Request__mach_vm_read_list_t __attribute__((unused)); 484 | #ifdef __MigPackStructs 485 | #pragma pack() 486 | #endif 487 | 488 | #ifdef __MigPackStructs 489 | #pragma pack(4) 490 | #endif 491 | typedef struct { 492 | mach_msg_header_t Head; 493 | /* start of the kernel processed data */ 494 | mach_msg_body_t msgh_body; 495 | mach_msg_ool_descriptor_t data; 496 | /* end of the kernel processed data */ 497 | NDR_record_t NDR; 498 | mach_vm_address_t address; 499 | mach_msg_type_number_t dataCnt; 500 | } __Request__mach_vm_write_t __attribute__((unused)); 501 | #ifdef __MigPackStructs 502 | #pragma pack() 503 | #endif 504 | 505 | #ifdef __MigPackStructs 506 | #pragma pack(4) 507 | #endif 508 | typedef struct { 509 | mach_msg_header_t Head; 510 | NDR_record_t NDR; 511 | mach_vm_address_t source_address; 512 | mach_vm_size_t size; 513 | mach_vm_address_t dest_address; 514 | } __Request__mach_vm_copy_t __attribute__((unused)); 515 | #ifdef __MigPackStructs 516 | #pragma pack() 517 | #endif 518 | 519 | #ifdef __MigPackStructs 520 | #pragma pack(4) 521 | #endif 522 | typedef struct { 523 | mach_msg_header_t Head; 524 | NDR_record_t NDR; 525 | mach_vm_address_t address; 526 | mach_vm_size_t size; 527 | mach_vm_address_t data; 528 | } __Request__mach_vm_read_overwrite_t __attribute__((unused)); 529 | #ifdef __MigPackStructs 530 | #pragma pack() 531 | #endif 532 | 533 | #ifdef __MigPackStructs 534 | #pragma pack(4) 535 | #endif 536 | typedef struct { 537 | mach_msg_header_t Head; 538 | NDR_record_t NDR; 539 | mach_vm_address_t address; 540 | mach_vm_size_t size; 541 | vm_sync_t sync_flags; 542 | } __Request__mach_vm_msync_t __attribute__((unused)); 543 | #ifdef __MigPackStructs 544 | #pragma pack() 545 | #endif 546 | 547 | #ifdef __MigPackStructs 548 | #pragma pack(4) 549 | #endif 550 | typedef struct { 551 | mach_msg_header_t Head; 552 | NDR_record_t NDR; 553 | mach_vm_address_t address; 554 | mach_vm_size_t size; 555 | vm_behavior_t new_behavior; 556 | } __Request__mach_vm_behavior_set_t __attribute__((unused)); 557 | #ifdef __MigPackStructs 558 | #pragma pack() 559 | #endif 560 | 561 | #ifdef __MigPackStructs 562 | #pragma pack(4) 563 | #endif 564 | typedef struct { 565 | mach_msg_header_t Head; 566 | /* start of the kernel processed data */ 567 | mach_msg_body_t msgh_body; 568 | mach_msg_port_descriptor_t object; 569 | /* end of the kernel processed data */ 570 | NDR_record_t NDR; 571 | mach_vm_address_t address; 572 | mach_vm_size_t size; 573 | mach_vm_offset_t mask; 574 | int flags; 575 | memory_object_offset_t offset; 576 | boolean_t copy; 577 | vm_prot_t cur_protection; 578 | vm_prot_t max_protection; 579 | vm_inherit_t inheritance; 580 | } __Request__mach_vm_map_t __attribute__((unused)); 581 | #ifdef __MigPackStructs 582 | #pragma pack() 583 | #endif 584 | 585 | #ifdef __MigPackStructs 586 | #pragma pack(4) 587 | #endif 588 | typedef struct { 589 | mach_msg_header_t Head; 590 | NDR_record_t NDR; 591 | mach_vm_address_t address; 592 | mach_vm_size_t size; 593 | vm_machine_attribute_t attribute; 594 | vm_machine_attribute_val_t value; 595 | } __Request__mach_vm_machine_attribute_t __attribute__((unused)); 596 | #ifdef __MigPackStructs 597 | #pragma pack() 598 | #endif 599 | 600 | #ifdef __MigPackStructs 601 | #pragma pack(4) 602 | #endif 603 | typedef struct { 604 | mach_msg_header_t Head; 605 | /* start of the kernel processed data */ 606 | mach_msg_body_t msgh_body; 607 | mach_msg_port_descriptor_t src_task; 608 | /* end of the kernel processed data */ 609 | NDR_record_t NDR; 610 | mach_vm_address_t target_address; 611 | mach_vm_size_t size; 612 | mach_vm_offset_t mask; 613 | int flags; 614 | mach_vm_address_t src_address; 615 | boolean_t copy; 616 | vm_inherit_t inheritance; 617 | } __Request__mach_vm_remap_t __attribute__((unused)); 618 | #ifdef __MigPackStructs 619 | #pragma pack() 620 | #endif 621 | 622 | #ifdef __MigPackStructs 623 | #pragma pack(4) 624 | #endif 625 | typedef struct { 626 | mach_msg_header_t Head; 627 | NDR_record_t NDR; 628 | mach_vm_offset_t offset; 629 | } __Request__mach_vm_page_query_t __attribute__((unused)); 630 | #ifdef __MigPackStructs 631 | #pragma pack() 632 | #endif 633 | 634 | #ifdef __MigPackStructs 635 | #pragma pack(4) 636 | #endif 637 | typedef struct { 638 | mach_msg_header_t Head; 639 | NDR_record_t NDR; 640 | mach_vm_address_t address; 641 | natural_t nesting_depth; 642 | mach_msg_type_number_t infoCnt; 643 | } __Request__mach_vm_region_recurse_t __attribute__((unused)); 644 | #ifdef __MigPackStructs 645 | #pragma pack() 646 | #endif 647 | 648 | #ifdef __MigPackStructs 649 | #pragma pack(4) 650 | #endif 651 | typedef struct { 652 | mach_msg_header_t Head; 653 | NDR_record_t NDR; 654 | mach_vm_address_t address; 655 | vm_region_flavor_t flavor; 656 | mach_msg_type_number_t infoCnt; 657 | } __Request__mach_vm_region_t __attribute__((unused)); 658 | #ifdef __MigPackStructs 659 | #pragma pack() 660 | #endif 661 | 662 | #ifdef __MigPackStructs 663 | #pragma pack(4) 664 | #endif 665 | typedef struct { 666 | mach_msg_header_t Head; 667 | /* start of the kernel processed data */ 668 | mach_msg_body_t msgh_body; 669 | mach_msg_port_descriptor_t parent_handle; 670 | /* end of the kernel processed data */ 671 | NDR_record_t NDR; 672 | memory_object_size_t size; 673 | memory_object_offset_t offset; 674 | vm_prot_t permission; 675 | } __Request___mach_make_memory_entry_t __attribute__((unused)); 676 | #ifdef __MigPackStructs 677 | #pragma pack() 678 | #endif 679 | 680 | #ifdef __MigPackStructs 681 | #pragma pack(4) 682 | #endif 683 | typedef struct { 684 | mach_msg_header_t Head; 685 | NDR_record_t NDR; 686 | mach_vm_address_t address; 687 | vm_purgable_t control; 688 | int state; 689 | } __Request__mach_vm_purgable_control_t __attribute__((unused)); 690 | #ifdef __MigPackStructs 691 | #pragma pack() 692 | #endif 693 | 694 | #ifdef __MigPackStructs 695 | #pragma pack(4) 696 | #endif 697 | typedef struct { 698 | mach_msg_header_t Head; 699 | NDR_record_t NDR; 700 | mach_vm_address_t address; 701 | vm_page_info_flavor_t flavor; 702 | mach_msg_type_number_t infoCnt; 703 | } __Request__mach_vm_page_info_t __attribute__((unused)); 704 | #ifdef __MigPackStructs 705 | #pragma pack() 706 | #endif 707 | 708 | #ifdef __MigPackStructs 709 | #pragma pack(4) 710 | #endif 711 | typedef struct { 712 | mach_msg_header_t Head; 713 | NDR_record_t NDR; 714 | mach_vm_offset_t address; 715 | mach_vm_size_t size; 716 | mach_vm_address_t dispositions; 717 | mach_vm_size_t dispositions_count; 718 | } __Request__mach_vm_page_range_query_t __attribute__((unused)); 719 | #ifdef __MigPackStructs 720 | #pragma pack() 721 | #endif 722 | #endif /* !__Request__mach_vm_subsystem__defined */ 723 | 724 | /* union of all requests */ 725 | 726 | #ifndef __RequestUnion__mach_vm_subsystem__defined 727 | #define __RequestUnion__mach_vm_subsystem__defined 728 | union __RequestUnion__mach_vm_subsystem { 729 | __Request__mach_vm_allocate_t Request_mach_vm_allocate; 730 | __Request__mach_vm_deallocate_t Request_mach_vm_deallocate; 731 | __Request__mach_vm_protect_t Request_mach_vm_protect; 732 | __Request__mach_vm_inherit_t Request_mach_vm_inherit; 733 | __Request__mach_vm_read_t Request_mach_vm_read; 734 | __Request__mach_vm_read_list_t Request_mach_vm_read_list; 735 | __Request__mach_vm_write_t Request_mach_vm_write; 736 | __Request__mach_vm_copy_t Request_mach_vm_copy; 737 | __Request__mach_vm_read_overwrite_t Request_mach_vm_read_overwrite; 738 | __Request__mach_vm_msync_t Request_mach_vm_msync; 739 | __Request__mach_vm_behavior_set_t Request_mach_vm_behavior_set; 740 | __Request__mach_vm_map_t Request_mach_vm_map; 741 | __Request__mach_vm_machine_attribute_t Request_mach_vm_machine_attribute; 742 | __Request__mach_vm_remap_t Request_mach_vm_remap; 743 | __Request__mach_vm_page_query_t Request_mach_vm_page_query; 744 | __Request__mach_vm_region_recurse_t Request_mach_vm_region_recurse; 745 | __Request__mach_vm_region_t Request_mach_vm_region; 746 | __Request___mach_make_memory_entry_t Request__mach_make_memory_entry; 747 | __Request__mach_vm_purgable_control_t Request_mach_vm_purgable_control; 748 | __Request__mach_vm_page_info_t Request_mach_vm_page_info; 749 | __Request__mach_vm_page_range_query_t Request_mach_vm_page_range_query; 750 | }; 751 | #endif /* !__RequestUnion__mach_vm_subsystem__defined */ 752 | /* typedefs for all replies */ 753 | 754 | #ifndef __Reply__mach_vm_subsystem__defined 755 | #define __Reply__mach_vm_subsystem__defined 756 | 757 | #ifdef __MigPackStructs 758 | #pragma pack(4) 759 | #endif 760 | typedef struct { 761 | mach_msg_header_t Head; 762 | NDR_record_t NDR; 763 | kern_return_t RetCode; 764 | mach_vm_address_t address; 765 | } __Reply__mach_vm_allocate_t __attribute__((unused)); 766 | #ifdef __MigPackStructs 767 | #pragma pack() 768 | #endif 769 | 770 | #ifdef __MigPackStructs 771 | #pragma pack(4) 772 | #endif 773 | typedef struct { 774 | mach_msg_header_t Head; 775 | NDR_record_t NDR; 776 | kern_return_t RetCode; 777 | } __Reply__mach_vm_deallocate_t __attribute__((unused)); 778 | #ifdef __MigPackStructs 779 | #pragma pack() 780 | #endif 781 | 782 | #ifdef __MigPackStructs 783 | #pragma pack(4) 784 | #endif 785 | typedef struct { 786 | mach_msg_header_t Head; 787 | NDR_record_t NDR; 788 | kern_return_t RetCode; 789 | } __Reply__mach_vm_protect_t __attribute__((unused)); 790 | #ifdef __MigPackStructs 791 | #pragma pack() 792 | #endif 793 | 794 | #ifdef __MigPackStructs 795 | #pragma pack(4) 796 | #endif 797 | typedef struct { 798 | mach_msg_header_t Head; 799 | NDR_record_t NDR; 800 | kern_return_t RetCode; 801 | } __Reply__mach_vm_inherit_t __attribute__((unused)); 802 | #ifdef __MigPackStructs 803 | #pragma pack() 804 | #endif 805 | 806 | #ifdef __MigPackStructs 807 | #pragma pack(4) 808 | #endif 809 | typedef struct { 810 | mach_msg_header_t Head; 811 | /* start of the kernel processed data */ 812 | mach_msg_body_t msgh_body; 813 | mach_msg_ool_descriptor_t data; 814 | /* end of the kernel processed data */ 815 | NDR_record_t NDR; 816 | mach_msg_type_number_t dataCnt; 817 | } __Reply__mach_vm_read_t __attribute__((unused)); 818 | #ifdef __MigPackStructs 819 | #pragma pack() 820 | #endif 821 | 822 | #ifdef __MigPackStructs 823 | #pragma pack(4) 824 | #endif 825 | typedef struct { 826 | mach_msg_header_t Head; 827 | NDR_record_t NDR; 828 | kern_return_t RetCode; 829 | mach_vm_read_entry_t data_list; 830 | } __Reply__mach_vm_read_list_t __attribute__((unused)); 831 | #ifdef __MigPackStructs 832 | #pragma pack() 833 | #endif 834 | 835 | #ifdef __MigPackStructs 836 | #pragma pack(4) 837 | #endif 838 | typedef struct { 839 | mach_msg_header_t Head; 840 | NDR_record_t NDR; 841 | kern_return_t RetCode; 842 | } __Reply__mach_vm_write_t __attribute__((unused)); 843 | #ifdef __MigPackStructs 844 | #pragma pack() 845 | #endif 846 | 847 | #ifdef __MigPackStructs 848 | #pragma pack(4) 849 | #endif 850 | typedef struct { 851 | mach_msg_header_t Head; 852 | NDR_record_t NDR; 853 | kern_return_t RetCode; 854 | } __Reply__mach_vm_copy_t __attribute__((unused)); 855 | #ifdef __MigPackStructs 856 | #pragma pack() 857 | #endif 858 | 859 | #ifdef __MigPackStructs 860 | #pragma pack(4) 861 | #endif 862 | typedef struct { 863 | mach_msg_header_t Head; 864 | NDR_record_t NDR; 865 | kern_return_t RetCode; 866 | mach_vm_size_t outsize; 867 | } __Reply__mach_vm_read_overwrite_t __attribute__((unused)); 868 | #ifdef __MigPackStructs 869 | #pragma pack() 870 | #endif 871 | 872 | #ifdef __MigPackStructs 873 | #pragma pack(4) 874 | #endif 875 | typedef struct { 876 | mach_msg_header_t Head; 877 | NDR_record_t NDR; 878 | kern_return_t RetCode; 879 | } __Reply__mach_vm_msync_t __attribute__((unused)); 880 | #ifdef __MigPackStructs 881 | #pragma pack() 882 | #endif 883 | 884 | #ifdef __MigPackStructs 885 | #pragma pack(4) 886 | #endif 887 | typedef struct { 888 | mach_msg_header_t Head; 889 | NDR_record_t NDR; 890 | kern_return_t RetCode; 891 | } __Reply__mach_vm_behavior_set_t __attribute__((unused)); 892 | #ifdef __MigPackStructs 893 | #pragma pack() 894 | #endif 895 | 896 | #ifdef __MigPackStructs 897 | #pragma pack(4) 898 | #endif 899 | typedef struct { 900 | mach_msg_header_t Head; 901 | NDR_record_t NDR; 902 | kern_return_t RetCode; 903 | mach_vm_address_t address; 904 | } __Reply__mach_vm_map_t __attribute__((unused)); 905 | #ifdef __MigPackStructs 906 | #pragma pack() 907 | #endif 908 | 909 | #ifdef __MigPackStructs 910 | #pragma pack(4) 911 | #endif 912 | typedef struct { 913 | mach_msg_header_t Head; 914 | NDR_record_t NDR; 915 | kern_return_t RetCode; 916 | vm_machine_attribute_val_t value; 917 | } __Reply__mach_vm_machine_attribute_t __attribute__((unused)); 918 | #ifdef __MigPackStructs 919 | #pragma pack() 920 | #endif 921 | 922 | #ifdef __MigPackStructs 923 | #pragma pack(4) 924 | #endif 925 | typedef struct { 926 | mach_msg_header_t Head; 927 | NDR_record_t NDR; 928 | kern_return_t RetCode; 929 | mach_vm_address_t target_address; 930 | vm_prot_t cur_protection; 931 | vm_prot_t max_protection; 932 | } __Reply__mach_vm_remap_t __attribute__((unused)); 933 | #ifdef __MigPackStructs 934 | #pragma pack() 935 | #endif 936 | 937 | #ifdef __MigPackStructs 938 | #pragma pack(4) 939 | #endif 940 | typedef struct { 941 | mach_msg_header_t Head; 942 | NDR_record_t NDR; 943 | kern_return_t RetCode; 944 | integer_t disposition; 945 | integer_t ref_count; 946 | } __Reply__mach_vm_page_query_t __attribute__((unused)); 947 | #ifdef __MigPackStructs 948 | #pragma pack() 949 | #endif 950 | 951 | #ifdef __MigPackStructs 952 | #pragma pack(4) 953 | #endif 954 | typedef struct { 955 | mach_msg_header_t Head; 956 | NDR_record_t NDR; 957 | kern_return_t RetCode; 958 | mach_vm_address_t address; 959 | mach_vm_size_t size; 960 | natural_t nesting_depth; 961 | mach_msg_type_number_t infoCnt; 962 | int info[19]; 963 | } __Reply__mach_vm_region_recurse_t __attribute__((unused)); 964 | #ifdef __MigPackStructs 965 | #pragma pack() 966 | #endif 967 | 968 | #ifdef __MigPackStructs 969 | #pragma pack(4) 970 | #endif 971 | typedef struct { 972 | mach_msg_header_t Head; 973 | /* start of the kernel processed data */ 974 | mach_msg_body_t msgh_body; 975 | mach_msg_port_descriptor_t object_name; 976 | /* end of the kernel processed data */ 977 | NDR_record_t NDR; 978 | mach_vm_address_t address; 979 | mach_vm_size_t size; 980 | mach_msg_type_number_t infoCnt; 981 | int info[10]; 982 | } __Reply__mach_vm_region_t __attribute__((unused)); 983 | #ifdef __MigPackStructs 984 | #pragma pack() 985 | #endif 986 | 987 | #ifdef __MigPackStructs 988 | #pragma pack(4) 989 | #endif 990 | typedef struct { 991 | mach_msg_header_t Head; 992 | /* start of the kernel processed data */ 993 | mach_msg_body_t msgh_body; 994 | mach_msg_port_descriptor_t object_handle; 995 | /* end of the kernel processed data */ 996 | NDR_record_t NDR; 997 | memory_object_size_t size; 998 | } __Reply___mach_make_memory_entry_t __attribute__((unused)); 999 | #ifdef __MigPackStructs 1000 | #pragma pack() 1001 | #endif 1002 | 1003 | #ifdef __MigPackStructs 1004 | #pragma pack(4) 1005 | #endif 1006 | typedef struct { 1007 | mach_msg_header_t Head; 1008 | NDR_record_t NDR; 1009 | kern_return_t RetCode; 1010 | int state; 1011 | } __Reply__mach_vm_purgable_control_t __attribute__((unused)); 1012 | #ifdef __MigPackStructs 1013 | #pragma pack() 1014 | #endif 1015 | 1016 | #ifdef __MigPackStructs 1017 | #pragma pack(4) 1018 | #endif 1019 | typedef struct { 1020 | mach_msg_header_t Head; 1021 | NDR_record_t NDR; 1022 | kern_return_t RetCode; 1023 | mach_msg_type_number_t infoCnt; 1024 | int info[32]; 1025 | } __Reply__mach_vm_page_info_t __attribute__((unused)); 1026 | #ifdef __MigPackStructs 1027 | #pragma pack() 1028 | #endif 1029 | 1030 | #ifdef __MigPackStructs 1031 | #pragma pack(4) 1032 | #endif 1033 | typedef struct { 1034 | mach_msg_header_t Head; 1035 | NDR_record_t NDR; 1036 | kern_return_t RetCode; 1037 | mach_vm_size_t dispositions_count; 1038 | } __Reply__mach_vm_page_range_query_t __attribute__((unused)); 1039 | #ifdef __MigPackStructs 1040 | #pragma pack() 1041 | #endif 1042 | #endif /* !__Reply__mach_vm_subsystem__defined */ 1043 | 1044 | /* union of all replies */ 1045 | 1046 | #ifndef __ReplyUnion__mach_vm_subsystem__defined 1047 | #define __ReplyUnion__mach_vm_subsystem__defined 1048 | union __ReplyUnion__mach_vm_subsystem { 1049 | __Reply__mach_vm_allocate_t Reply_mach_vm_allocate; 1050 | __Reply__mach_vm_deallocate_t Reply_mach_vm_deallocate; 1051 | __Reply__mach_vm_protect_t Reply_mach_vm_protect; 1052 | __Reply__mach_vm_inherit_t Reply_mach_vm_inherit; 1053 | __Reply__mach_vm_read_t Reply_mach_vm_read; 1054 | __Reply__mach_vm_read_list_t Reply_mach_vm_read_list; 1055 | __Reply__mach_vm_write_t Reply_mach_vm_write; 1056 | __Reply__mach_vm_copy_t Reply_mach_vm_copy; 1057 | __Reply__mach_vm_read_overwrite_t Reply_mach_vm_read_overwrite; 1058 | __Reply__mach_vm_msync_t Reply_mach_vm_msync; 1059 | __Reply__mach_vm_behavior_set_t Reply_mach_vm_behavior_set; 1060 | __Reply__mach_vm_map_t Reply_mach_vm_map; 1061 | __Reply__mach_vm_machine_attribute_t Reply_mach_vm_machine_attribute; 1062 | __Reply__mach_vm_remap_t Reply_mach_vm_remap; 1063 | __Reply__mach_vm_page_query_t Reply_mach_vm_page_query; 1064 | __Reply__mach_vm_region_recurse_t Reply_mach_vm_region_recurse; 1065 | __Reply__mach_vm_region_t Reply_mach_vm_region; 1066 | __Reply___mach_make_memory_entry_t Reply__mach_make_memory_entry; 1067 | __Reply__mach_vm_purgable_control_t Reply_mach_vm_purgable_control; 1068 | __Reply__mach_vm_page_info_t Reply_mach_vm_page_info; 1069 | __Reply__mach_vm_page_range_query_t Reply_mach_vm_page_range_query; 1070 | }; 1071 | #endif /* !__RequestUnion__mach_vm_subsystem__defined */ 1072 | 1073 | #ifndef subsystem_to_name_map_mach_vm 1074 | #define subsystem_to_name_map_mach_vm \ 1075 | { "mach_vm_allocate", 4800 },\ 1076 | { "mach_vm_deallocate", 4801 },\ 1077 | { "mach_vm_protect", 4802 },\ 1078 | { "mach_vm_inherit", 4803 },\ 1079 | { "mach_vm_read", 4804 },\ 1080 | { "mach_vm_read_list", 4805 },\ 1081 | { "mach_vm_write", 4806 },\ 1082 | { "mach_vm_copy", 4807 },\ 1083 | { "mach_vm_read_overwrite", 4808 },\ 1084 | { "mach_vm_msync", 4809 },\ 1085 | { "mach_vm_behavior_set", 4810 },\ 1086 | { "mach_vm_map", 4811 },\ 1087 | { "mach_vm_machine_attribute", 4812 },\ 1088 | { "mach_vm_remap", 4813 },\ 1089 | { "mach_vm_page_query", 4814 },\ 1090 | { "mach_vm_region_recurse", 4815 },\ 1091 | { "mach_vm_region", 4816 },\ 1092 | { "_mach_make_memory_entry", 4817 },\ 1093 | { "mach_vm_purgable_control", 4818 },\ 1094 | { "mach_vm_page_info", 4819 },\ 1095 | { "mach_vm_page_range_query", 4820 } 1096 | #endif 1097 | 1098 | #ifdef __AfterMigUserHeader 1099 | __AfterMigUserHeader 1100 | #endif /* __AfterMigUserHeader */ 1101 | 1102 | #endif /* _mach_vm_user_ */ 1103 | -------------------------------------------------------------------------------- /Package/DEBIAN/control: -------------------------------------------------------------------------------- 1 | Package: flexdecrypt 2 | Name: flexdecrypt 3 | Depends: firmware (>=12.2) | org.swift.libswift (>=5.0), firmware (>= 9.0) 4 | Author: John Coates 5 | Maintainer: John Coates 6 | Description: Tool for decrypting iOS apps and Mach-O binaries. 7 | Version: 1.1 8 | Section: Tools 9 | Architecture: iphoneos-arm 10 | -------------------------------------------------------------------------------- /Readme.md: -------------------------------------------------------------------------------- 1 | ## iOS App & Mach-O binary decryption 2 | This is a decryption tool for research purposes. It uses mremap_encrypted to decrypt a file from disk. 3 | 4 | ### Installation 5 | 1. Download the .deb package from the [the latest release.](https://github.com/JohnCoates/flexdecrypt/releases/latest) 6 | 2. Transfer it to your device. 7 | 3. Use Filza to install it via UI, or use the command line: `dpkg -i flexdecrypt.deb` 8 | 9 | If you're on iOS 12.1 or lower, use dpkg directly, and receive an error, you may need to resolve dependencies with: `apt-get -f -y --allow-unauthenticated install` 10 | 11 | Latest release also includes the flexdecrypt binary in case you want to install it yourself. 12 | 13 | ### Build from source 14 | Open the project file with Xcode. 15 | Use the Debug scheme to run directly on your device from Xcode, with debugger support. 16 | Configure the run arguments with Xcode's scheme editor. 17 | Make sure you have [AppSync](https://cydia.akemi.ai/) installed so the app installs despite the custom entitlements. 18 | 19 | 20 | ### Information 21 | 22 | Further reading at https://www.linkedin.com/pulse/decrypting-apps-ios-john-coates/ 23 | 24 | Contact: john@johncoates.dev 25 | -------------------------------------------------------------------------------- /Scripts/build.sh: -------------------------------------------------------------------------------- 1 | set -x 2 | set -e 3 | 4 | scriptsDirectory=`dirname "$0"` 5 | projectDirectory="$scriptsDirectory/../" 6 | 7 | pushd "$projectDirectory" 8 | xcodebuild -scheme flexdecrypt -sdk iphoneos -configuration Release -derivedDataPath ./derived 9 | binDirectory="./Package/usr/bin" 10 | mkdir -p "$binDirectory" 11 | cp ./derived/Build/Products/Release-iphoneos/flexdecrypt.app/flexdecrypt "$binDirectory/" 12 | find ./Package -name ".DS_Store" -depth -exec rm {} \; 13 | dpkg-deb -b -Zgzip ./Package flexdecrypt.deb 14 | popd 15 | -------------------------------------------------------------------------------- /Source/Binary Reading/BinaryError.swift: -------------------------------------------------------------------------------- 1 | // 2 | // BinaryError.swift 3 | // Created on 6/12/20 4 | // 5 | 6 | import Foundation 7 | 8 | enum BinaryError: Error { 9 | case notEnoughData 10 | case tooMuchData 11 | case invalidString(bytes: [UInt8]) 12 | case message(_ message: String) 13 | } 14 | -------------------------------------------------------------------------------- /Source/Binary Reading/DataConvertible.swift: -------------------------------------------------------------------------------- 1 | // 2 | // DataConvertible.swift 3 | // Created on 6/12/20 4 | // 5 | 6 | import Foundation 7 | 8 | enum Endian { 9 | case big 10 | case little 11 | } 12 | 13 | protocol DataConvertible { 14 | init(data: Data, endian: Endian) throws 15 | } 16 | 17 | extension DataConvertible where Self: FixedWidthInteger { 18 | init(data: Data, endian: Endian = .little) throws { 19 | var value: Self = 0 20 | let valueSize = MemoryLayout.size(ofValue: value) 21 | guard data.count == valueSize else { 22 | if data.count < valueSize { 23 | throw BinaryError.notEnoughData 24 | } else { 25 | throw BinaryError.tooMuchData 26 | } 27 | } 28 | 29 | _ = withUnsafeMutablePointer(to: &value, { 30 | data.copyBytes(to: UnsafeMutableBufferPointer(start: $0, count: 1)) 31 | }) 32 | 33 | self = value 34 | if case .big = endian { 35 | self = self.bigEndian 36 | } 37 | } 38 | } 39 | 40 | extension UInt8: DataConvertible {} 41 | extension Int8: DataConvertible {} 42 | extension UInt16: DataConvertible {} 43 | extension Int16: DataConvertible {} 44 | extension UInt32: DataConvertible {} 45 | extension Int32: DataConvertible {} 46 | extension UInt64: DataConvertible {} 47 | extension Int64: DataConvertible {} 48 | extension UInt: DataConvertible {} 49 | extension Int: DataConvertible {} 50 | -------------------------------------------------------------------------------- /Source/Binary Reading/DataView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // DataView.swift 3 | // Created on 6/12/20 4 | // 5 | 6 | import Foundation 7 | 8 | struct DataView { 9 | let data: Data 10 | var offset: Int 11 | var pointer: UnsafeMutableRawPointer? 12 | var startAddress: UInt? 13 | var endAddress: UInt? 14 | var slide: Int? 15 | 16 | init(data: Data, offset: Int = 0, pointer: UnsafeMutableRawPointer? = nil, slide: Int? = nil) { 17 | self.data = data 18 | self.offset = offset 19 | self.pointer = pointer 20 | if let slide = slide { 21 | self.slide = slide 22 | } 23 | if let pointer = pointer { 24 | let start = UInt(bitPattern: pointer) 25 | let end = start + UInt(data.count) 26 | startAddress = start 27 | endAddress = end 28 | } 29 | } 30 | 31 | mutating func read(endian: Endian = .little) throws -> T { 32 | let size = MemoryLayout.size 33 | let range: Range = offset.. String? { 44 | var bytes = [UInt8]() 45 | while bytes.last != 0 { 46 | try bytes.append(read()) 47 | } 48 | 49 | return String(bytes: bytes.dropLast(), encoding: .utf8) 50 | } 51 | 52 | func immutableReadString() throws -> String { 53 | var copy = self 54 | var bytes = [UInt8]() 55 | 56 | while bytes.last != 0 { 57 | try bytes.append(copy.read()) 58 | } 59 | bytes = bytes.dropLast() 60 | 61 | guard let string = String(bytes: bytes, encoding: .utf8) else { 62 | throw BinaryError.invalidString(bytes: bytes) 63 | } 64 | 65 | return string 66 | } 67 | 68 | func with(offset: Int) -> DataView { 69 | var copy = self 70 | copy.offset = offset 71 | return copy 72 | } 73 | 74 | /// Use address if this data view has address information. 75 | /// Otherwise fallback to offset. 76 | func with(offset: Int?, address: UInt, slid: Bool) throws -> DataView { 77 | if let offset = offset, slide == nil { 78 | return with(offset: offset) 79 | } 80 | 81 | return try with(address: address, slid: slid) 82 | } 83 | 84 | func with(address: UInt, slid: Bool) throws -> DataView { 85 | let (target, start, end) = try self.info(forAddress: address, slid: slid) 86 | 87 | guard target >= start, target < end else { 88 | throw Error.addressOutOfBounds(address: target) 89 | } 90 | 91 | var copy = self 92 | copy.offset = Int(target - start) 93 | return copy 94 | } 95 | 96 | func withCString(offset: Int?, address: UInt, slid: Bool) throws -> DataView { 97 | if let offset = offset, slide == nil { 98 | return with(offset: offset) 99 | } 100 | 101 | let target = try self.info(forAddress: address, slid: slid).target 102 | 103 | guard let pointer = UnsafePointer(bitPattern: target) else { 104 | throw Error.invalidAddress(address: target) 105 | } 106 | 107 | var position = pointer 108 | while position.pointee != 0 { 109 | position = position.advanced(by: 1) 110 | } 111 | 112 | let bytes = pointer.distance(to: position) + 1 113 | return try with(offset: nil, address: address, slid: slid, bytes: bytes) 114 | } 115 | 116 | func with(offset: Int?, address: UInt, slid: Bool, targetType: T.Type) throws -> DataView { 117 | let bytes = MemoryLayout.size 118 | return try with(offset: offset, address: address, slid: slid, bytes: bytes) 119 | } 120 | 121 | func with(offset: Int?, address: UInt, slid: Bool, bytes: Int) throws -> DataView { 122 | if let offset = offset, slide == nil { 123 | return with(offset: offset) 124 | } 125 | 126 | let (target, start, end) = try self.info(forAddress: address, slid: slid) 127 | if target >= start, target < end { 128 | var copy = self 129 | copy.offset = Int(target - start) 130 | return copy 131 | } 132 | 133 | guard let pointer = UnsafeMutableRawPointer(bitPattern: target) else { 134 | throw Error.invalidAddress(address: target) 135 | } 136 | let data = Data(bytesNoCopy: pointer, count: bytes, deallocator: .none) 137 | return DataView(data: data, offset: 0, pointer: pointer, slide: 0) 138 | } 139 | 140 | // Utilities 141 | 142 | private func info(forAddress address: UInt, slid: Bool) throws -> (target: UInt, start: UInt, end: UInt) { 143 | guard let slide = slide, let start = startAddress, let end = endAddress else { 144 | throw Error.missingAddressInformation 145 | } 146 | let target: UInt 147 | if slid { 148 | target = address 149 | } else { 150 | target = UInt(Int(address) + slide) 151 | } 152 | return (target: target, start: start, end: end) 153 | } 154 | 155 | enum Error: Swift.Error { 156 | case missingAddressInformation 157 | case addressOutOfBounds(address: UInt) 158 | case invalidAddress(address: UInt) 159 | } 160 | } 161 | -------------------------------------------------------------------------------- /Source/Bridging.h: -------------------------------------------------------------------------------- 1 | // 2 | // Use this file to import your target's public headers that you would like to expose to Swift. 3 | // 4 | 5 | #import "FLXSystemApi.h" 6 | #import "FLXPrivateApi.h" 7 | -------------------------------------------------------------------------------- /Source/C API Wrappers/FLXPrivateApi.h: -------------------------------------------------------------------------------- 1 | // 2 | // FLXPrivateApi.h 3 | // Created on 10/4/19 4 | // 5 | 6 | #import 7 | 8 | NS_ASSUME_NONNULL_BEGIN 9 | 10 | @interface FLXPrivateApi : NSObject 11 | 12 | @property (class, readonly) BOOL allowInvalidCodesignedMemoryEnabled; 13 | + (BOOL)allowInvalidCodesignedMemory; 14 | 15 | /// int mremap_encrypted(caddr_t addr, size_t len, 16 | /// uint32_t cryptid, uint32_t cputype, 17 | /// uint32_t cpusubtype); 18 | + (int)mremap_encrypted:(NSUInteger)address 19 | length:(size_t)length 20 | cryptId:(uint32_t)cryptId 21 | cpuType:(uint32_t)cpuType 22 | cpuSubType:(uint32_t)cpuSubType 23 | NS_SWIFT_NAME(mremap_encrypted(address:length:cryptId:cpuType:cpuSubType:)); 24 | 25 | @end 26 | 27 | NS_ASSUME_NONNULL_END 28 | -------------------------------------------------------------------------------- /Source/C API Wrappers/FLXPrivateApi.mm: -------------------------------------------------------------------------------- 1 | // 2 | // FLXPrivateApi.m 3 | // Created on 10/4/19 4 | // 5 | 6 | #import "FLXPrivateApi.h" 7 | #import 8 | #define PT_TRACE_ME 0 /* child declares it's being traced */ 9 | #define PT_ATTACH 10 /* trace some running process */ 10 | #define PT_DETACH 11 /* stop tracing a process */ 11 | #define PT_ATTACHEXC 14 /* attach to running process with signal exception */ 12 | 13 | #define CS_OPS_STATUS 0 /* return status */ 14 | /* process is currently or has previously been debugged and allowed to run with invalid pages */ 15 | #define CS_DEBUGGED 0x10000000 16 | 17 | #define FORK_IS_CHILD 0 18 | #define FORK_FAILURE -1 19 | 20 | // External 21 | extern "C" { 22 | int csops(pid_t pid, unsigned int ops, void * useraddr, size_t usersize); 23 | extern int mremap_encrypted(caddr_t addr, size_t len, 24 | uint32_t cryptid, uint32_t cputype, 25 | uint32_t cpusubtype); 26 | }; 27 | 28 | @implementation FLXPrivateApi 29 | 30 | static BOOL allowsInvalidCodesignedMemoryEnabled = FALSE; 31 | 32 | + (BOOL)allowInvalidCodesignedMemoryEnabled { 33 | if (allowsInvalidCodesignedMemoryEnabled) { 34 | return TRUE; 35 | } 36 | 37 | uint32_t flags; 38 | csops(getpid(), CS_OPS_STATUS, &flags, 0); 39 | if (flags & CS_DEBUGGED){ 40 | return TRUE; 41 | } else { 42 | return FALSE; 43 | } 44 | } 45 | 46 | + (BOOL)allowInvalidCodesignedMemory { 47 | pid_t pid = fork(); 48 | 49 | if (pid == FORK_IS_CHILD) { 50 | #pragma clang diagnostic push 51 | #pragma clang diagnostic ignored "-Wdeprecated-declarations" 52 | syscall(SYS_ptrace, PT_TRACE_ME, 0, 0, 0); 53 | #pragma clang diagnostic pop 54 | exit(0); 55 | } else if (pid == FORK_FAILURE) { 56 | int error = errno; 57 | const char *errorMessage = strerror(error); 58 | NSLog(@"fork failed: %d - %s", error, errorMessage); 59 | return FALSE; 60 | } 61 | 62 | allowsInvalidCodesignedMemoryEnabled = TRUE; 63 | return TRUE; 64 | } 65 | 66 | + (int)mremap_encrypted:(NSUInteger)address 67 | length:(size_t)length 68 | cryptId:(uint32_t)cryptId 69 | cpuType:(uint32_t)cpuType 70 | cpuSubType:(uint32_t)cpuSubType { 71 | return mremap_encrypted((caddr_t)address, length, 72 | cryptId, cpuType, cpuSubType); 73 | } 74 | 75 | @end 76 | -------------------------------------------------------------------------------- /Source/C API Wrappers/FLXSystemApi.h: -------------------------------------------------------------------------------- 1 | // 2 | // FLXSystemApi.h 3 | // Created on 10/4/19 4 | // 5 | 6 | #import 7 | #import 8 | 9 | NS_ASSUME_NONNULL_BEGIN 10 | 11 | @interface FLXSystemApi : NSObject 12 | 13 | /// int open(const char *path, int oflag, ...); 14 | + (int)openPath:(NSString *)path flag:(int)flag mode:(int)mode NS_SWIFT_NAME(open(path:flag:mode:)); 15 | 16 | /// void * mmap(void *addr, size_t len, int prot, int flags, int fd, off_t offset); 17 | + (NSUInteger)mmap:(NSUInteger)address 18 | length:(size_t)length 19 | protection:(int)protection 20 | flags:(int)flags 21 | fileDescriptor:(int)fileDescriptor 22 | offset:(NSUInteger)offset NS_SWIFT_NAME(mmap(address:length:protection:flags:fileDescriptor:offset:)); 23 | 24 | // int munmap(void *addr, size_t len); 25 | + (int)munmap:(NSUInteger)address length:(size_t)length 26 | NS_SWIFT_NAME(munmap(address:length:)); 27 | 28 | /// char *strerror(int errnum); 29 | + (NSString *)stringFromError:(int)errorCode 30 | NS_SWIFT_NAME(string(fromError:)); 31 | 32 | // kern_return_t vm_allocate(mach_task_self(), vm_address_t *address, vm_size_t size, int flags); 33 | + (kern_return_t)vm_allocate:(NSUInteger *)address size:(NSUInteger)size flags:(int)flags; 34 | 35 | // kern_return_t vm_protect (vm_task_t target_task, vm_address_t address, vm_size_t size, boolean_t set_maximum, vm_prot_t new_protection); 36 | + (kern_return_t)vm_protect:(NSUInteger)address size:(NSUInteger)size setMaximum:(BOOL)maximum newProtection:(int)newProtection; 37 | 38 | // kern_return_t vm_deallocate(mach_task_self(), vm_address_t address, vm_size_t size); 39 | + (kern_return_t)vm_deallocate:(NSUInteger)address size:(NSUInteger)size; 40 | 41 | // int posix_spawn(pid_t *restrict pid, const char *restrict path, const posix_spawn_file_actions_t *file_actions, 42 | // const posix_spawnattr_t *restrict attrp, char *const argv[restrict], char *const envp[restrict]); 43 | // result = posix_spawn (&pid, path, &file_actions, &attributes, argv, envp); 44 | + (int)posix_spawnWithPidOut:(pid_t *)pid path:(NSString *)path 45 | fileActions:(const posix_spawn_file_actions_t _Nullable * _Nullable)fileActions 46 | attributes:(const posix_spawnattr_t _Nullable * _Nullable)attributes; 47 | 48 | + (uintptr_t)executableAddressFromSuspendedTask:(mach_port_name_t)task; 49 | 50 | + (nullable NSData *)readTask:(mach_port_name_t)task address:(uintptr_t)address length:(size_t)length; 51 | 52 | @end 53 | 54 | NS_ASSUME_NONNULL_END 55 | -------------------------------------------------------------------------------- /Source/C API Wrappers/FLXSystemApi.m: -------------------------------------------------------------------------------- 1 | // 2 | // FLXSystemApi.m 3 | // Created on 10/4/19 4 | // 5 | 6 | #import "FLXSystemApi.h" 7 | #import 8 | #import 9 | #import 10 | 11 | @implementation FLXSystemApi 12 | 13 | + (int)openPath:(NSString *)path flag:(int)flag mode:(int)mode NS_SWIFT_NAME(open(path:flag:mode:)) { 14 | return open(path.UTF8String, flag, mode); 15 | } 16 | 17 | + (NSUInteger)mmap:(NSUInteger)address 18 | length:(size_t)length 19 | protection:(int)protection 20 | flags:(int)flags 21 | fileDescriptor:(int)fileDescriptor 22 | offset:(NSUInteger)offset NS_SWIFT_NAME(mmap(address:length:protection:flags:fileDescriptor:offset:)) { 23 | return (NSUInteger)mmap((void *)address, length, protection, flags, fileDescriptor, offset); 24 | } 25 | 26 | + (int)munmap:(NSUInteger)address length:(size_t)length 27 | NS_SWIFT_NAME(munmap(address:length:)) { 28 | return munmap((void *)address, length); 29 | } 30 | 31 | + (NSString *)stringFromError:(int)errorCode 32 | NS_SWIFT_NAME(string(fromError:)) { 33 | return @(strerror(errorCode)); 34 | } 35 | 36 | // MARK: - VM Allocations 37 | 38 | /* 39 | kern_return_t vm_allocate 40 | ( 41 | vm_map_t target_task, 42 | vm_address_t *address, 43 | vm_size_t size, 44 | int flags 45 | ); 46 | */ 47 | + (kern_return_t)vm_allocate:(NSUInteger *)address size:(NSUInteger)size flags:(int)flags { 48 | // kern_return_t r = vm_alloc(&addr, size, VM_FLAGS_ANYWHERE | VM_MAKE_TAG(VM_MEMORY_DYLIB)); 49 | // vm_allocate(mach_task_self(), addr, size, flags); 50 | 51 | vm_address_t addressOut; 52 | kern_return_t result = vm_allocate(mach_task_self(), &addressOut, size, flags); 53 | if (result == KERN_SUCCESS) { 54 | *address = (NSUInteger)addressOut; 55 | } 56 | 57 | return result; 58 | } 59 | 60 | // kern_return_t vm_protect (vm_task_t target_task, vm_address_t address, vm_size_t size, boolean_t set_maximum, vm_prot_t new_protection) 61 | + (kern_return_t)vm_protect:(NSUInteger)address size:(NSUInteger)size setMaximum:(BOOL)maximum newProtection:(vm_prot_t)newProtection { 62 | return vm_protect(mach_task_self(), (vm_address_t)address, (vm_size_t)size, maximum, newProtection); 63 | } 64 | 65 | /* 66 | kern_return_t vm_deallocate 67 | ( 68 | vm_map_t target_task, 69 | vm_address_t address, 70 | vm_size_t size 71 | ); 72 | */ 73 | + (kern_return_t)vm_deallocate:(NSUInteger)address size:(NSUInteger)size { 74 | return vm_deallocate(mach_task_self(), (vm_address_t)address, (vm_size_t)size); 75 | } 76 | 77 | extern char **environ; 78 | + (int)posix_spawnWithPidOut:(pid_t *)pid path:(NSString *)path 79 | fileActions:(const posix_spawn_file_actions_t _Nullable * _Nullable)fileActions 80 | attributes:(const posix_spawnattr_t _Nullable * _Nullable)attributes { 81 | char *argv[] = { 82 | (char *)path.UTF8String, 83 | NULL 84 | }; 85 | return posix_spawn(pid, path.UTF8String, fileActions, attributes, argv, environ); 86 | } 87 | 88 | 89 | + (uintptr_t)executableAddressFromSuspendedTask:(mach_port_name_t)task { 90 | thread_act_array_t threads; 91 | mach_msg_type_number_t threadCount = 0; 92 | kern_return_t result = task_threads(task, &threads, &threadCount); 93 | 94 | if (result != 0) { 95 | NSLog(@"task_threads error: 0x%x %s", result, mach_error_string(result)); 96 | return 0; 97 | } 98 | 99 | mach_port_t targetThread = threads[0]; 100 | 101 | mach_msg_type_number_t stateCount; 102 | thread_state_flavor_t stateFlavor; 103 | 104 | #if defined(__arm__) && !defined(__aarch64__) 105 | stateFlavor = ARM_THREAD_STATE32; 106 | stateCount = ARM_THREAD_STATE32_COUNT; 107 | arm_thread_state_t state; 108 | #elif defined(__aarch64__) 109 | stateFlavor = ARM_THREAD_STATE64; 110 | stateCount = ARM_THREAD_STATE64_COUNT; 111 | arm_thread_state64_t state; 112 | #elif defined(__x86_64__) 113 | stateFlavor = x86_THREAD_STATE; 114 | stateCount = x86_THREAD_STATE_COUNT; 115 | struct __darwin_x86_thread_state64 state; 116 | #else 117 | #error "Unsupported architecture" 118 | #endif 119 | 120 | result = thread_get_state(targetThread, stateFlavor, (thread_state_t)&state, &stateCount); 121 | 122 | if (result != 0) { 123 | NSLog(@"thread_get_state error: 0x%x %s", result, mach_error_string(result)); 124 | return 0; 125 | } 126 | 127 | #if defined(__arm__) || defined(__aarch64__) 128 | uintptr_t stackPointer = state.__sp; 129 | #else 130 | uintptr_t stackPointer = state.__rsp; 131 | #endif 132 | 133 | uintptr_t executableAddress = 0; 134 | mach_vm_size_t bytesWritten = 0; 135 | result = mach_vm_read_overwrite(task, stackPointer, sizeof(uintptr_t), 136 | (mach_vm_address_t)&executableAddress, &bytesWritten); 137 | if (result != 0 || bytesWritten != sizeof(uintptr_t)) { 138 | NSLog(@"mach_vm_read_overwrite error: 0x%x %s", result, mach_error_string(result)); 139 | return 0; 140 | } 141 | 142 | for (int index = 1; index < threadCount; index += 1) { 143 | mach_port_deallocate(mach_task_self_, threads[index]); 144 | } 145 | 146 | vm_deallocate(mach_task_self_, (vm_address_t) threads, threadCount * sizeof (thread_t)); 147 | 148 | return executableAddress; 149 | } 150 | 151 | + (NSData *)readTask:(mach_port_name_t)task address:(uintptr_t)address length:(size_t)length { 152 | NSMutableData *data = [NSMutableData dataWithLength:length]; 153 | mach_vm_size_t bytesWritten = 0; 154 | kern_return_t result = mach_vm_read_overwrite(task, address, length, 155 | (mach_vm_address_t)data.mutableBytes, &bytesWritten); 156 | if (result != 0 || bytesWritten != length) { 157 | NSLog(@"mach_vm_read_overwrite error: 0x%x %s", result, mach_error_string(result)); 158 | return nil; 159 | } 160 | 161 | return data; 162 | } 163 | 164 | @end 165 | -------------------------------------------------------------------------------- /Source/Commands/DecryptFile.swift: -------------------------------------------------------------------------------- 1 | // 2 | // DecryptFile.swift 3 | // Created on 6/30/20 4 | // 5 | 6 | import Foundation 7 | import ArgumentParser 8 | 9 | struct DecryptFile: ParsableCommand { 10 | static var configuration = CommandConfiguration(commandName: "file", abstract: "Decrypt file.") 11 | 12 | @Argument(help: "The file to decrypt.") 13 | var file: String 14 | 15 | @Option(name: .customLong("output"), help: "The path to the output file.") 16 | var output: String? 17 | var outputUrl: URL { 18 | if let output = output { 19 | return URL(fileURLWithPath: output) 20 | } else { 21 | let lastPathComponent = file.components(separatedBy: "/").last ?? "decrypted" 22 | return URL(fileURLWithPath: "/tmp/" + lastPathComponent) 23 | } 24 | } 25 | 26 | func run() throws { 27 | FLXLog.printInternalMessages = options.verboseOutput 28 | 29 | let file = try MachOFile(url: URL(fileURLWithPath: self.file)) 30 | let data = try file.sliceDataForHostArchitecture() 31 | try data.write(to: outputUrl) 32 | print("Wrote decrypted image to \(outputUrl.path)") 33 | } 34 | 35 | @OptionGroup() 36 | var options: Options 37 | } 38 | -------------------------------------------------------------------------------- /Source/Commands/FlexDecrypt.swift: -------------------------------------------------------------------------------- 1 | // 2 | // FlexDecrypt.swift 3 | // Created on 6/30/20 4 | // 5 | 6 | import Foundation 7 | import ArgumentParser 8 | 9 | struct FlexDecrypt: ParsableCommand { 10 | static var configuration = CommandConfiguration(abstract: "A tool for decrypting apps and Mach-O binaries. Based " + 11 | "on the Flex 3 jailbreak app's source code.", version: "1.0.0", 12 | subcommands: [DecryptFile.self], 13 | defaultSubcommand: DecryptFile.self 14 | ) 15 | } 16 | 17 | struct Options: ParsableArguments { 18 | @Flag(name: [.customLong("verbose"), .customShort("v")], 19 | help: "Use verbose output.") 20 | var verboseOutput = false 21 | } 22 | -------------------------------------------------------------------------------- /Source/Debugging/FLXLog.swift: -------------------------------------------------------------------------------- 1 | // 2 | // FLXLog.swift 3 | // Created on 6/30/20 4 | // 5 | 6 | import Foundation 7 | 8 | struct FLXLog { 9 | static func `internal`(_ message: String) { 10 | guard printInternalMessages else { return } 11 | print(message) 12 | } 13 | 14 | static var printInternalMessages = false 15 | } 16 | -------------------------------------------------------------------------------- /Source/Extensions/Int+Convenience.swift: -------------------------------------------------------------------------------- 1 | // 2 | // Int+Convenience.swift 3 | // Flexapp 4 | // 5 | // Created by John Coates on 11/9/16. 6 | // Copyright © 2016 John Coates. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | extension BinaryInteger { 12 | var hex: String { 13 | return String.init(self, radix: 16, uppercase: false) 14 | } 15 | } 16 | 17 | extension UInt64 { 18 | var untaggedPointer: UInt64 { 19 | // superclass example: 0x40080000000009e2 20 | return self & 0xFFFFFFFFFF 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /Source/Mach-O/Decrypt/MachOFile+Decrypt.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOFile+Decrypt.swift 3 | // Created on 6/30/20 4 | // 5 | 6 | import Foundation 7 | 8 | extension MachOFile { 9 | func decrypt(slice: MachOSlice) throws -> Data { 10 | for command in slice.loadCommands { 11 | switch command.type { 12 | case let .encryptionInfo(value): 13 | if value.cryptid == 0 { 14 | throw MachOError.notEncrypted 15 | } 16 | FLXLog.internal("Found encryption info") 17 | return try decrypt(slice: slice, encryptionInfo: value) 18 | default: 19 | break 20 | } 21 | } 22 | 23 | throw MachOError.noEncryptionLoadCommand 24 | } 25 | 26 | func decrypt(slice: MachOSlice, encryptionInfo: MachOEncryptionInfo) throws -> Data { 27 | let isApplication = slice.header.filetype == MachO.Filetype.execute.rawValue 28 | if isApplication { 29 | let pageSize = UInt(getpagesize()) 30 | let pageRemainder = UInt(encryptionInfo.cryptoff) % pageSize 31 | // Can't remap to decrypted unless crypt offset is on a page 32 | // Application needs to be launched so kernel juggles this. 33 | if pageRemainder != 0 || slice.hasCodesignDirectives { 34 | return try decryptApplication(slice: slice, encryptionInfo: encryptionInfo) 35 | } 36 | } 37 | 38 | if slice.hasCodesignDirectives { 39 | throw MachOError.codesignDirectivesNotSupportedForDecryption 40 | } 41 | 42 | // TODO: Support fat Mach-O 43 | FLXLog.internal("Opening file descriptor") 44 | let fileDescriptor = FLXSystemApi.open(path: fileUrl.path, flag: O_RDONLY, mode: 0) 45 | 46 | if fileDescriptor == -1 { 47 | throw MachOError.openFailed(error: popError()) 48 | } 49 | 50 | var segmentIndexAtFileOffsetZeroMaybe: Int? 51 | var segmentIndex = 0 52 | let allSegments = try slice.segments() 53 | let validSegments = allSegments.filter { $0.filesize > 0 } 54 | let sortedSegments = validSegments.sorted(by: { $0.vmaddr < $1.vmaddr }) 55 | 56 | guard let firstSegment = sortedSegments.first else { 57 | throw MachOError.message("Failed to find a segment with a valid vm address") 58 | } 59 | 60 | let vmStart = UInt(firstSegment.vmaddr) 61 | let vmEnd = try slice.segments().reduce(UInt(0), { (sum, segment) in 62 | let isPageZero = isApplication && segment.vmaddr == 0 63 | if isPageZero { return sum } 64 | 65 | let isRestrict = segment.segmentName == "__RESTRICT" 66 | if isRestrict { return sum } 67 | 68 | let end = segment.vmaddr + segment.filesize 69 | if end > sum { 70 | return UInt(end) 71 | } else { 72 | return sum 73 | } 74 | }) 75 | FLXLog.internal("VM start: \(vmStart.hex)") 76 | 77 | var allocatedAddress: UInt = 0 78 | let allocateSize = vmEnd - vmStart 79 | 80 | FLXLog.internal("Allocating \(allocateSize.hex) bytes") 81 | 82 | var allocateResult: kern_return_t = KERN_SUCCESS 83 | allocateResult = FLXSystemApi.vm_allocate(&allocatedAddress, 84 | size: allocateSize, 85 | flags: VM_FLAGS_ANYWHERE | (VM_MEMORY_DYLIB << 24 )) 86 | 87 | guard allocateResult == KERN_SUCCESS else { 88 | throw MachOError.vmAllocateFailed(error: "Failed to allocate \(allocateSize.hex) bytes, result: \(allocateResult)") 89 | } 90 | 91 | let didMap = FLXSystemApi.mmap(address: allocatedAddress, 92 | length: Int(allocateSize), 93 | protection: VM_PROT_READ, 94 | flags: MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS, 95 | fileDescriptor: 0, offset: 0) 96 | 97 | if didMap == UInt.max || didMap != allocatedAddress { 98 | throw MachOError.initialMmapFailed 99 | } 100 | 101 | let allocationEnd = allocatedAddress + allocateSize 102 | 103 | FLXLog.internal("Mapped \(allocatedAddress.hex) - \((allocatedAddress + allocateSize).hex)") 104 | 105 | let restrictAllocation: (() throws -> Void) = { 106 | let result = FLXSystemApi.vm_protect(allocatedAddress, size: allocateSize, setMaximum: true, newProtection: 0) 107 | guard result == KERN_SUCCESS else { 108 | throw MachOError.vmAllocateFailed(error: "Failed to restrict \(allocateSize.hex) bytes, result: \(result)") 109 | } 110 | 111 | FLXLog.internal("Restricted allocation to prevent memory mappings.") 112 | } 113 | 114 | let deallocAllocation: (() throws -> Void) = { 115 | let deallocateResult = FLXSystemApi.vm_deallocate(allocatedAddress, size: allocateSize) 116 | guard deallocateResult == KERN_SUCCESS else { 117 | throw MachOError.vmAllocateFailed(error: "Failed to de-allocate \(allocateSize.hex) bytes, result: \(deallocateResult)") 118 | } 119 | FLXLog.internal("Deallocating \(allocateSize.hex) at \(allocatedAddress.hex)") 120 | } 121 | 122 | var deallocateMemoryCallback: (() throws -> Void)? = { 123 | try restrictAllocation() 124 | try deallocAllocation() 125 | FLXLog.internal("Restricted allocation to prevent memory mappings.") 126 | FLXLog.internal("Unmapped segments") 127 | } 128 | 129 | defer { 130 | if let deallocateMemoryCallback = deallocateMemoryCallback { 131 | try? deallocateMemoryCallback() 132 | } 133 | } 134 | 135 | let slide: Int 136 | 137 | if allocatedAddress > vmStart { 138 | slide = Int(allocatedAddress) - Int(vmStart) 139 | } else { 140 | slide = Int(vmStart) - Int(allocatedAddress) 141 | } 142 | 143 | var segments: [MachOSegment] = [] 144 | var mappedSegments: [UInt] = [] 145 | 146 | let unmapMappedSegments: (() throws -> Void) = { 147 | try mappedSegments.enumerated().forEach { (offset, address) in 148 | let segment = segments[offset] 149 | let result = FLXSystemApi.munmap(address: address, length: Int(segment.filesize)) 150 | 151 | if result != 0 { 152 | FLXLog.internal("Unmapping failed for \(segment.segmentName) at \(address.hex)") 153 | throw MachOError.munmapFailed(segment: segment.segmentName, error: self.popError()) 154 | } 155 | } 156 | } 157 | 158 | deallocateMemoryCallback = { 159 | try unmapMappedSegments() 160 | try deallocAllocation() 161 | FLXLog.internal("Restricted allocation to prevent memory mappings.") 162 | // FLXLog.internal("Unmapped segments") 163 | } 164 | 165 | for segment in allSegments { 166 | let isPageZero = segment.vmaddr == 0 && isApplication 167 | if isPageZero { continue } 168 | 169 | let isRestrict = segment.segmentName == "__RESTRICT" 170 | if isRestrict { continue } 171 | 172 | if segment.fileoff == 0 && segment.filesize > 0 { 173 | segmentIndexAtFileOffsetZeroMaybe = segmentIndex 174 | } 175 | 176 | let mapAddress = UInt(Int(segment.vmaddr) + slide) 177 | let length = Int(segment.filesize) 178 | let endAddress: UInt = mapAddress + UInt(length) 179 | let mapped: UInt 180 | 181 | guard mapAddress >= allocatedAddress && endAddress <= allocationEnd else { 182 | if mapAddress < allocatedAddress { 183 | throw MachOError.message("Map address for \(segment.segmentName): \(mapAddress.hex) < \(allocatedAddress.hex)") 184 | } else { 185 | throw MachOError.message("End address for \(segment.segmentName): \(endAddress.hex) > \(allocationEnd.hex)") 186 | } 187 | } 188 | 189 | mapped = FLXSystemApi.mmap(address: mapAddress, 190 | length: length, 191 | protection: Int32(segment.initprot), 192 | flags: MAP_PRIVATE | MAP_FIXED, 193 | fileDescriptor: fileDescriptor, 194 | offset: UInt(segment.fileoff)) 195 | 196 | if mapped == UInt.max || mapped != mapAddress { 197 | throw MachOError.mmapFailed(segment: segment.segmentName, error: popError()) 198 | } 199 | 200 | FLXLog.internal("Mapped \(mapAddress.hex) - \(endAddress.hex)") 201 | 202 | mappedSegments.append(mapped) 203 | segments.append(segment) 204 | segmentIndex += 1 205 | } 206 | 207 | FLXLog.internal("Segments mapped, resuming verbosity.") 208 | FLXLog.internal("Allocation address: \(allocatedAddress.hex)") 209 | FLXLog.internal("Slide: \(slide.hex)") 210 | mappedSegments.enumerated().forEach { (index, mappedSegment) in 211 | let segment = segments[index] 212 | FLXLog.internal("Mapped \(segment.segmentName) to \(mappedSegment.hex) - bytes: \(segment.filesize.hex)") 213 | } 214 | 215 | guard let segmentIndexAtFileOffsetZero = segmentIndexAtFileOffsetZeroMaybe else { 216 | throw MachOError.missingSegmentAtFileOffsetZero 217 | } 218 | 219 | let segment = segments[segmentIndexAtFileOffsetZero] 220 | let mappedSegment = mappedSegments[segmentIndexAtFileOffsetZero] 221 | 222 | let offset = encryptionInfo.cryptoff 223 | let size = encryptionInfo.cryptsize 224 | let cpuType = UInt32(slice.header.cputype) 225 | let cpuSubType = UInt32(slice.header.cpusubtype) 226 | 227 | if FLXPrivateApi.allowInvalidCodesignedMemoryEnabled == false { 228 | FLXLog.internal("Allowing invalid codesigned memory") 229 | if FLXPrivateApi.allowInvalidCodesignedMemory() == false { 230 | throw MachOError.failedToAllowInvalidCodesignedMemory 231 | } 232 | } 233 | 234 | FLXLog.internal("Remapping \(segment.segmentName) to encrypted backing") 235 | let result = FLXPrivateApi.mremap_encrypted(address: mappedSegment + UInt(offset), 236 | length: Int(size), 237 | cryptId: encryptionInfo.cryptid, 238 | cpuType: cpuType, 239 | cpuSubType: cpuSubType) 240 | if result == -1 { 241 | throw MachOError.mremap_encryptedFailed(segment: segment.segmentName, error: popError()) 242 | } 243 | 244 | FLXLog.internal("Reading decrypted file") 245 | let capacity = segments.reduce(0, { $0 + $1.filesize }) 246 | FLXLog.internal("Bytes: \(capacity.hex)") 247 | var originalData = Data(capacity: Int(capacity)) 248 | var decryptedData = Data(capacity: Int(capacity)) 249 | 250 | try mappedSegments.enumerated().forEach { (index, address) in 251 | let segment = segments[index] 252 | guard let pointer = UnsafePointer.init(bitPattern: Int(address)) else { 253 | throw MachOError.mappingAddressToPointerFailed(address: address) 254 | } 255 | 256 | let fileSize = Int(segment.filesize) 257 | FLXLog.internal("Reading \(fileSize.hex) bytes at \(address.hex)") 258 | decryptedData.append(pointer, count: fileSize) 259 | originalData.append(slice.data[Int(segment.fileoff)...size) 278 | decryptedData.replaceSubrange(cryptIdStart...size)) 280 | 281 | return decryptedData 282 | } 283 | } 284 | 285 | -------------------------------------------------------------------------------- /Source/Mach-O/Decrypt/MachOFile+SpawnDecrypt.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOFile+SpawnDecrypt.swift 3 | // Created on 9/13/19 4 | // 5 | 6 | import Foundation 7 | 8 | extension MachOFile { 9 | func decryptApplication(slice: MachOSlice, encryptionInfo: MachOEncryptionInfo) throws -> Data { 10 | let isApplication = slice.header.filetype == MachO.Filetype.execute.rawValue 11 | guard isApplication else { 12 | throw MachOError.notAnApplication 13 | } 14 | 15 | var pid: pid_t = 0 16 | var fileActions: posix_spawn_file_actions_t? 17 | var attributes: posix_spawnattr_t? 18 | posix_spawn_file_actions_init(&fileActions) 19 | posix_spawnattr_init(&attributes) 20 | 21 | var signalMaskSet: sigset_t = 0 22 | sigemptyset(&signalMaskSet) 23 | posix_spawnattr_setsigmask(&attributes, &signalMaskSet) 24 | 25 | var flags: Int16 = 0 26 | flags |= Int16(POSIX_SPAWN_SETPGROUP) 27 | flags |= Int16(POSIX_SPAWN_SETSIGMASK) 28 | flags |= Int16(POSIX_SPAWN_START_SUSPENDED) 29 | posix_spawnattr_setflags(&attributes, flags) 30 | 31 | FLXLog.internal("Spawning \(fileUrl.path)") 32 | let result = FLXSystemApi.posix_spawn(withPidOut: &pid, path: fileUrl.path, 33 | fileActions: &fileActions, 34 | attributes: &attributes) 35 | 36 | let error = popError() 37 | posix_spawnattr_destroy(&attributes) 38 | posix_spawn_file_actions_destroy(&fileActions) 39 | 40 | if result != 0 { 41 | throw MachOError.message("Spawn failed with result #\(result): \(error)") 42 | } 43 | 44 | var task: mach_port_t = 0 45 | 46 | let taskResult = task_for_pid(mach_task_self_, pid, &task) 47 | if taskResult != 0 { 48 | throw MachOError.message("Failed to find get task, error: \(machError(code: taskResult))") 49 | } 50 | 51 | let executableAddress = FLXSystemApi.executableAddress(fromSuspendedTask: task) 52 | if executableAddress == 0 { 53 | throw MachOError.message("Failed to find executable address") 54 | } 55 | 56 | let segments = try slice.segments() 57 | .filter { $0.filesize > 0 } 58 | .sorted(by: { $0.vmaddr < $1.vmaddr }) 59 | 60 | let capacity = segments.map({$0.filesize}).reduce(0, +) 61 | var decryptedData = Data(capacity: Int(capacity)) 62 | let preferredLoadAddress = segments[0].vmaddr 63 | let slide = Int(executableAddress) - Int(preferredLoadAddress) 64 | for segment in segments { 65 | let address = Int(segment.vmaddr) + slide 66 | guard let data = FLXSystemApi.readTask(task, address: UInt(address), length: Int(segment.filesize)) else { 67 | throw MachOError.message("Failed to read segment \(segment.segmentName)") 68 | } 69 | decryptedData.append(data) 70 | } 71 | 72 | FLXLog.internal("Terminating process") 73 | kill(pid, SIGKILL) 74 | waitpid(pid, nil, 0) 75 | 76 | // Modify encryption flag 77 | let cryptIdStart = decryptedData.startIndex.advanced(by: encryptionInfo.cryptIdOffset) 78 | let cryptIdEnd = cryptIdStart.advanced(by: MemoryLayout.size) 79 | decryptedData.replaceSubrange(cryptIdStart...size)) 81 | 82 | return decryptedData 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /Source/Mach-O/MachOBinary.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOBinary.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOBinary { 9 | let data: Data 10 | var mutableData: Data 11 | 12 | init(fileUrl: URL) { 13 | guard let data = try? Data.init(contentsOf: fileUrl) else { 14 | fatalError("Failed to read \(fileUrl.path)") 15 | } 16 | self.data = data 17 | mutableData = data 18 | } 19 | 20 | var slices: [MachOSlice] { 21 | var view = DataView(data: data) 22 | do { 23 | let magic: UInt32 = try view.read() 24 | if magic == MachO.Magic.arch32.rawValue || magic == MachO.Magic.arch64.rawValue { 25 | return try [MachOSlice(data: data)] 26 | } else if magic == MachO.Magic.fat.rawValue { 27 | var slices = [MachOSlice]() 28 | view = view.with(offset: 0) 29 | 30 | let fatHeader = try MachO.fat_header(dataView: &view) 31 | for _ in 0.. = offset.. Data { 22 | FLXLog.internal("Identifying best slice for \(fileUrl.path)") 23 | let slice = try sliceForHostArchitecture() 24 | if decryptIfEncrypted && slice.isEncrypted { 25 | FLXLog.internal("Decrypting slice") 26 | return try decrypt(slice: slice) 27 | } else { 28 | FLXLog.internal("Not encrypted") 29 | return slice.data 30 | } 31 | } 32 | 33 | private func sliceForHostArchitecture() throws -> MachOSlice { 34 | let binary = MachOBinary(fileUrl: self.fileUrl) 35 | let slices = binary.slices 36 | 37 | guard let localArch = NXGetLocalArchInfo()?.pointee else { 38 | throw MachOError.noHostArchitecture 39 | } 40 | 41 | var bestSlice: MachOSlice? 42 | 43 | for slice in slices { 44 | if bestSlice == nil { 45 | bestSlice = slice 46 | continue 47 | } 48 | 49 | if slice.header.cputype == localArch.cputype { 50 | FLXLog.internal("found slice for cputype") 51 | bestSlice = slice 52 | if slice.header.cpusubtype == localArch.cpusubtype { 53 | FLXLog.internal("found slice for cpusubtype") 54 | break 55 | } 56 | } 57 | } 58 | 59 | guard let slice = bestSlice else { 60 | throw MachOError.noSlices 61 | } 62 | 63 | return slice 64 | } 65 | 66 | func bytesDifference(original: Data, decrypted: Data, maximum: Int) -> Int { 67 | var difference = 0 68 | for index in 0..= maximum { 75 | break 76 | } 77 | } 78 | 79 | return difference 80 | } 81 | 82 | var name: String { 83 | return fileUrl.deletingPathExtension().lastPathComponent 84 | } 85 | 86 | func popError() -> String { 87 | let error = errno 88 | let errorString = FLXSystemApi.string(fromError: error) 89 | return "#\(error): \(errorString)" 90 | } 91 | 92 | func machError(code: kern_return_t) -> String { 93 | let errorString = mach_error_string(code) 94 | return "#\(code): \(errorString.debugDescription)" 95 | } 96 | } 97 | -------------------------------------------------------------------------------- /Source/Mach-O/MachOSlice.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOSlice.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOSlice { 9 | enum Error: Swift.Error { 10 | case missingSymbolTable 11 | } 12 | 13 | let data: Data 14 | var mutableData: Data 15 | let fileRange: Range 16 | let header: MachOHeader 17 | 18 | init(data: Data, fileRange: Range? = nil) throws { 19 | self.data = data 20 | if let range = fileRange { 21 | self.fileRange = range 22 | } else { 23 | self.fileRange = 0.. [MachOSegment] { 80 | var segments: [MachOSegment] = [] 81 | 82 | for command in loadCommands { 83 | switch command.type { 84 | case let .segment(segment): 85 | segments.append(segment) 86 | default: 87 | break 88 | } 89 | } 90 | return segments 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/ArchitectureValue.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ArchitectureValue.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | enum ArchitectureValue { 9 | case arch32(data: Architecture32) 10 | case arch64(data: Architecture64) 11 | 12 | var size: Int { 13 | switch self { 14 | case .arch32: 15 | return MemoryLayout.size 16 | case .arch64: 17 | return MemoryLayout.size 18 | } 19 | } 20 | } 21 | 22 | enum Architecture { 23 | case arch32 24 | case arch64 25 | } 26 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOEncryptionInfo.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOEncryptionInfo.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOEncryptionInfo { 9 | private let value: ArchitectureValue 10 | 11 | let view: DataView 12 | 13 | init(dataView view: inout DataView) throws { 14 | self.view = view 15 | var copy = view 16 | let cmd: UInt32 = try copy.read() 17 | if cmd == MachO.LoadCommands.encryptionInfo32.rawValue { 18 | value = try .arch32(data: MachO.encryption_info_command_32(dataView: &view)) 19 | } else if cmd == MachO.LoadCommands.encryptionInfo64.rawValue { 20 | value = try .arch64(data: MachO.encryption_info_command_64(dataView: &view)) 21 | } else { 22 | throw MachOError.message("Invalid encryption command value: \(cmd)") 23 | } 24 | } 25 | 26 | var cryptoff: UInt32 { 27 | switch value { 28 | case let .arch32(data): 29 | return data.cryptoff 30 | case let.arch64(data): 31 | return data.cryptoff 32 | } 33 | } 34 | 35 | var cryptsize: UInt32 { 36 | switch value { 37 | case let .arch32(data): 38 | return data.cryptsize 39 | case let.arch64(data): 40 | return data.cryptsize 41 | } 42 | } 43 | 44 | var cryptid: UInt32 { 45 | switch value { 46 | case let .arch32(data): 47 | return data.cryptid 48 | case let.arch64(data): 49 | return data.cryptid 50 | } 51 | } 52 | 53 | var pad: UInt32 { 54 | switch value { 55 | case .arch32: 56 | return 0 57 | case let.arch64(data): 58 | return data.pad 59 | } 60 | } 61 | 62 | var cryptIdOffset: Int { 63 | return view.offset + MemoryLayout.size * 4 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOHeader+DataConvertible.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOHeader+DataConvertible.swift 3 | // Created on 5/22/19 4 | // 5 | 6 | import Foundation 7 | 8 | protocol DataConvertibleStruct { 9 | init(data: Data, endian: Endian) throws 10 | init(dataView view: inout DataView, endian: Endian) throws 11 | } 12 | 13 | extension MachO.mach_header: DataConvertible, DataConvertibleStruct { 14 | init(dataView view: inout DataView, endian: Endian = .little) throws { 15 | magic = try view.read(endian: endian) 16 | cputype = try view.read(endian: endian) 17 | cpusubtype = try view.read(endian: endian) 18 | filetype = try view.read(endian: endian) 19 | ncmds = try view.read(endian: endian) 20 | sizeofcmds = try view.read(endian: endian) 21 | flags = try view.read(endian: endian) 22 | } 23 | } 24 | 25 | extension MachO.mach_header_64: DataConvertible { 26 | init(data: Data, endian: Endian = .little) throws { 27 | let size = MemoryLayout.size 28 | guard data.count == size else { 29 | if data.count < size { 30 | throw BinaryError.notEnoughData 31 | } else { 32 | throw BinaryError.tooMuchData 33 | } 34 | } 35 | 36 | var view = DataView(data: data) 37 | try self.init(dataView: &view, endian: endian) 38 | } 39 | 40 | init(dataView view: inout DataView, endian: Endian = .little) throws { 41 | magic = try view.read(endian: endian) 42 | cputype = try view.read(endian: endian) 43 | cpusubtype = try view.read(endian: endian) 44 | filetype = try view.read(endian: endian) 45 | ncmds = try view.read(endian: endian) 46 | sizeofcmds = try view.read(endian: endian) 47 | flags = try view.read(endian: endian) 48 | reserved = try view.read(endian: endian) 49 | } 50 | } 51 | 52 | extension MachO.fat_header: DataConvertible { 53 | init(data: Data, endian: Endian = .little) throws { 54 | let size = MemoryLayout.size 55 | guard data.count == size else { 56 | if data.count < size { 57 | throw BinaryError.notEnoughData 58 | } else { 59 | throw BinaryError.tooMuchData 60 | } 61 | } 62 | 63 | var view = DataView(data: data) 64 | try self.init(dataView: &view, endian: endian) 65 | } 66 | 67 | init(dataView view: inout DataView, endian: Endian = .little) throws { 68 | magic = try view.read(endian: endian) 69 | nfat_arch = try view.read(endian: .big) 70 | } 71 | } 72 | 73 | extension DataConvertibleStruct { 74 | init(data: Data, endian: Endian = .little) throws { 75 | let size = MemoryLayout.size 76 | guard data.count == size else { 77 | if data.count < size { 78 | throw BinaryError.notEnoughData 79 | } else { 80 | throw BinaryError.tooMuchData 81 | } 82 | } 83 | 84 | var view = DataView(data: data) 85 | try self.init(dataView: &view, endian: endian) 86 | } 87 | } 88 | 89 | extension MachO.fat_arch: DataConvertible, DataConvertibleStruct { 90 | init(dataView view: inout DataView, endian: Endian = .little) throws { 91 | cputype = try view.read(endian: .big) 92 | cpusubtype = try view.read(endian: .big) 93 | offset = try view.read(endian: .big) 94 | size = try view.read(endian: .big) 95 | align = try view.read(endian: .big) 96 | } 97 | } 98 | 99 | // MARK: - Load Commands 100 | 101 | extension MachO.load_command: DataConvertible, DataConvertibleStruct { 102 | init(dataView view: inout DataView, endian: Endian = .little) throws { 103 | let offset = view.offset 104 | cmd = try view.read(endian: endian) 105 | cmdsize = try view.read(endian: endian) 106 | view.offset = offset + Int(cmdsize) 107 | } 108 | } 109 | 110 | extension MachO.segment_command: DataConvertible, DataConvertibleStruct { 111 | init(dataView view: inout DataView, endian: Endian = .little) throws { 112 | cmd = try view.read(endian: endian) 113 | cmdsize = try view.read(endian: endian) 114 | segname.0 = try view.read() 115 | segname.1 = try view.read() 116 | segname.2 = try view.read() 117 | segname.3 = try view.read() 118 | segname.4 = try view.read() 119 | segname.5 = try view.read() 120 | segname.6 = try view.read() 121 | segname.7 = try view.read() 122 | segname.8 = try view.read() 123 | segname.9 = try view.read() 124 | segname.10 = try view.read() 125 | segname.11 = try view.read() 126 | segname.12 = try view.read() 127 | segname.13 = try view.read() 128 | segname.14 = try view.read() 129 | segname.15 = try view.read() 130 | vmaddr = try view.read(endian: endian) 131 | vmsize = try view.read(endian: endian) 132 | fileoff = try view.read(endian: endian) 133 | filesize = try view.read(endian: endian) 134 | maxprot = try view.read(endian: endian) 135 | initprot = try view.read(endian: endian) 136 | nsects = try view.read(endian: endian) 137 | flags = try view.read(endian: endian) 138 | } 139 | 140 | var segmentName: String { 141 | let mirror = Mirror(reflecting: segname) 142 | let bytes: [UInt8] = mirror.children.map({ UInt8($0.value as! Int8) }) 143 | let string = String(cString: bytes) 144 | return string 145 | } 146 | } 147 | 148 | extension MachO.segment_command_64: DataConvertible, DataConvertibleStruct { 149 | init(dataView view: inout DataView, endian: Endian = .little) throws { 150 | cmd = try view.read(endian: endian) 151 | cmdsize = try view.read(endian: endian) 152 | segname.0 = try view.read() 153 | segname.1 = try view.read() 154 | segname.2 = try view.read() 155 | segname.3 = try view.read() 156 | segname.4 = try view.read() 157 | segname.5 = try view.read() 158 | segname.6 = try view.read() 159 | segname.7 = try view.read() 160 | segname.8 = try view.read() 161 | segname.9 = try view.read() 162 | segname.10 = try view.read() 163 | segname.11 = try view.read() 164 | segname.12 = try view.read() 165 | segname.13 = try view.read() 166 | segname.14 = try view.read() 167 | segname.15 = try view.read() 168 | vmaddr = try view.read(endian: endian) 169 | vmsize = try view.read(endian: endian) 170 | fileoff = try view.read(endian: endian) 171 | filesize = try view.read(endian: endian) 172 | maxprot = try view.read(endian: endian) 173 | initprot = try view.read(endian: endian) 174 | nsects = try view.read(endian: endian) 175 | flags = try view.read(endian: endian) 176 | } 177 | 178 | var segmentName: String { 179 | let mirror = Mirror(reflecting: segname) 180 | let bytes: [UInt8] = mirror.children.map({ UInt8($0.value as! Int8) }) 181 | let string = String(cString: bytes) 182 | return string 183 | } 184 | } 185 | 186 | extension MachO.encryption_info_command_32: DataConvertible, DataConvertibleStruct { 187 | init(dataView view: inout DataView, endian: Endian = .little) throws { 188 | cmd = try view.read(endian: endian) 189 | cmdsize = try view.read(endian: endian) 190 | cryptoff = try view.read(endian: endian) 191 | cryptsize = try view.read(endian: endian) 192 | cryptid = try view.read(endian: endian) 193 | } 194 | } 195 | 196 | extension MachO.encryption_info_command_64: DataConvertible, DataConvertibleStruct { 197 | init(dataView view: inout DataView, endian: Endian = .little) throws { 198 | cmd = try view.read(endian: endian) 199 | cmdsize = try view.read(endian: endian) 200 | cryptoff = try view.read(endian: endian) 201 | cryptsize = try view.read(endian: endian) 202 | cryptid = try view.read(endian: endian) 203 | pad = try view.read(endian: endian) 204 | } 205 | } 206 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOHeader.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOHeader.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOHeader { 9 | private let value: ArchitectureValue 10 | init(view: inout DataView) throws { 11 | var copy = view 12 | let magic: UInt32 = try copy.read() 13 | if magic == MachO.Magic.arch32.rawValue { 14 | value = try .arch32(data: MachO.mach_header(dataView: &view)) 15 | } else if magic == MachO.Magic.arch64.rawValue { 16 | value = try .arch64(data: MachO.mach_header_64(dataView: &view)) 17 | } else { 18 | throw MachOError.message("Invalid slice magic: \(magic) @ offset \(view.offset)") 19 | } 20 | } 21 | 22 | var magic: UInt32 { 23 | switch value { 24 | case let .arch32(data): 25 | return data.magic 26 | case let.arch64(data): 27 | return data.magic 28 | } 29 | } 30 | 31 | var cputype: cpu_type_t { 32 | switch value { 33 | case let .arch32(data): 34 | return data.cputype 35 | case let.arch64(data): 36 | return data.cputype 37 | } 38 | } 39 | 40 | var cpusubtype: cpu_subtype_t { 41 | switch value { 42 | case let .arch32(data): 43 | return data.cpusubtype 44 | case let.arch64(data): 45 | return data.cpusubtype 46 | } 47 | } 48 | 49 | var filetype: UInt32 { 50 | switch value { 51 | case let .arch32(data): 52 | return data.filetype 53 | case let.arch64(data): 54 | return data.filetype 55 | } 56 | } 57 | 58 | var ncmds: UInt32 { 59 | switch value { 60 | case let .arch32(data): 61 | return data.ncmds 62 | case let.arch64(data): 63 | return data.ncmds 64 | } 65 | } 66 | 67 | var sizeofcmds: UInt32 { 68 | switch value { 69 | case let .arch32(data): 70 | return data.sizeofcmds 71 | case let.arch64(data): 72 | return data.sizeofcmds 73 | } 74 | } 75 | 76 | var flags: UInt32 { 77 | switch value { 78 | case let .arch32(data): 79 | return data.flags 80 | case let.arch64(data): 81 | return data.flags 82 | } 83 | } 84 | 85 | var reserved: UInt32 { 86 | switch value { 87 | case .arch32: 88 | return 0 89 | case let.arch64(data): 90 | return data.reserved 91 | } 92 | } 93 | 94 | var size: Int { 95 | return value.size 96 | } 97 | } 98 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOLoadCommand.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOLoadCommand.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOLoadCommand { 9 | enum CommandType { 10 | case segment(value: MachOSegment) 11 | // case id(value: MachODylibCommand) 12 | // case symbolTable(value: MachOSymbolTable) 13 | case encryptionInfo(value: MachOEncryptionInfo) 14 | // case codeSignature(value: MachOLinkeditDataCommand) 15 | case noAssociatedValue 16 | 17 | init(command: MachO.LoadCommands, view: inout DataView) throws { 18 | switch command { 19 | // case .symbolTable: 20 | // self = try .symbolTable(value: MachOSymbolTable(dataView: &view)) 21 | case .segment32, .segment64: 22 | self = try .segment(value: MachOSegment(view: &view)) 23 | // case .id, .loadDylib, 24 | // .loadWeakDylib: 25 | // self = try .id(value: MachODylibCommand(dataView: &view)) 26 | case .encryptionInfo32, .encryptionInfo64: 27 | self = try .encryptionInfo(value: MachOEncryptionInfo(dataView: &view)) 28 | // case .codeSignature: 29 | // self = try .codeSignature(value: MachOLinkeditDataCommand(dataView: &view)) 30 | case .codesignDirectives: 31 | self = .noAssociatedValue 32 | } 33 | } 34 | } 35 | 36 | private let value: MachO.load_command 37 | init?(view: inout DataView) throws { 38 | var copy = view 39 | let value = try MachO.load_command(dataView: ©) 40 | defer { 41 | view.offset += Int(value.cmdsize) 42 | } 43 | guard let command = MachO.LoadCommands(rawValue: value.cmd) else { 44 | return nil 45 | } 46 | copy = view 47 | type = try CommandType(command: command, view: ©) 48 | self.cmd = command 49 | self.value = value 50 | } 51 | 52 | let cmd: MachO.LoadCommands 53 | var type: CommandType 54 | 55 | var cmdsize: UInt32 { 56 | return value.cmdsize 57 | } 58 | } 59 | 60 | extension MachOLoadCommand: CustomStringConvertible { 61 | var description: String { 62 | return "MachOLoadCommand: \(type)" 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOSegment.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOSegment.swift 3 | // Created on 10/5/19 4 | // 5 | 6 | import Foundation 7 | 8 | struct MachOSegment { 9 | private let value: ArchitectureValue 10 | let architecture: Architecture 11 | private let view: DataView 12 | 13 | init(view: inout DataView) throws { 14 | var copy = view 15 | let cmd: UInt32 = try copy.read() 16 | 17 | if cmd == MachO.LoadCommands.segment32.rawValue { 18 | architecture = .arch32 19 | value = try .arch32(data: MachO.segment_command(dataView: &view)) 20 | } else if cmd == MachO.LoadCommands.segment64.rawValue { 21 | architecture = .arch64 22 | value = try .arch64(data: MachO.segment_command_64(dataView: &view)) 23 | } else { 24 | throw MachOError.message("Invalid segment command value: \(cmd)") 25 | } 26 | 27 | self.view = view 28 | } 29 | 30 | var segmentName: String { 31 | switch value { 32 | case let .arch32(data): 33 | return data.segmentName 34 | case let.arch64(data): 35 | return data.segmentName 36 | } 37 | } 38 | 39 | var vmaddr: UInt64 { 40 | switch value { 41 | case let .arch32(data): 42 | return UInt64(data.vmaddr) 43 | case let.arch64(data): 44 | return data.vmaddr 45 | } 46 | } 47 | 48 | var vmsize: UInt64 { 49 | switch value { 50 | case let .arch32(data): 51 | return UInt64(data.vmsize) 52 | case let.arch64(data): 53 | return data.vmsize 54 | } 55 | } 56 | 57 | var fileoff: UInt64 { 58 | switch value { 59 | case let .arch32(data): 60 | return UInt64(data.fileoff) 61 | case let.arch64(data): 62 | return data.fileoff 63 | } 64 | } 65 | 66 | var filesize: UInt64 { 67 | switch value { 68 | case let .arch32(data): 69 | return UInt64(data.filesize) 70 | case let.arch64(data): 71 | return data.filesize 72 | } 73 | } 74 | 75 | var maxprot: vm_prot_t { 76 | switch value { 77 | case let .arch32(data): 78 | return data.maxprot 79 | case let.arch64(data): 80 | return data.maxprot 81 | } 82 | } 83 | 84 | var initprot: vm_prot_t { 85 | switch value { 86 | case let .arch32(data): 87 | return data.initprot 88 | case let.arch64(data): 89 | return data.initprot 90 | } 91 | } 92 | 93 | var nsects: UInt32 { 94 | switch value { 95 | case let .arch32(data): 96 | return data.nsects 97 | case let.arch64(data): 98 | return data.nsects 99 | } 100 | } 101 | 102 | var flags: UInt32 { 103 | switch value { 104 | case let .arch32(data): 105 | return data.flags 106 | case let.arch64(data): 107 | return data.flags 108 | } 109 | } 110 | } 111 | -------------------------------------------------------------------------------- /Source/Mach-O/Structure/MachOStructs.swift: -------------------------------------------------------------------------------- 1 | // 2 | // MachOStructs.swift 3 | // Created on 5/24/19 4 | // 5 | // swiftlint:disable large_tuple 6 | 7 | import Foundation 8 | import MachO 9 | 10 | struct MachO { 11 | enum Magic: UInt32 { 12 | case arch32 = 0xfeedface 13 | case arch64 = 0xfeedfacf 14 | case fat = 0xbebafeca 15 | } 16 | 17 | enum Filetype: UInt32 { 18 | case execute = 0x2 19 | case dylib = 0x6 20 | } 21 | 22 | struct mach_header { 23 | var magic: UInt32 /* mach magic number identifier */ 24 | var cputype: cpu_type_t /* cpu specifier */ 25 | var cpusubtype: cpu_subtype_t /* machine specifier */ 26 | var filetype: UInt32 /* type of file */ 27 | var ncmds: UInt32 /* number of load commands */ 28 | var sizeofcmds: UInt32 /* the size of all the load commands */ 29 | var flags: UInt32 /* flags */ 30 | } 31 | 32 | struct mach_header_64 { 33 | var magic: UInt32 /* mach magic number identifier */ 34 | var cputype: cpu_type_t /* cpu specifier */ 35 | var cpusubtype: cpu_subtype_t /* machine specifier */ 36 | var filetype: UInt32 /* type of file */ 37 | var ncmds: UInt32 /* number of load commands */ 38 | var sizeofcmds: UInt32 /* the size of all the load commands */ 39 | var flags: UInt32 /* flags */ 40 | var reserved: UInt32 /* reserved */ 41 | } 42 | 43 | public struct fat_header { 44 | public var magic: UInt32 /* FAT_MAGIC or FAT_MAGIC_64 */ 45 | public var nfat_arch: UInt32 /* number of structs that follow */ 46 | } 47 | 48 | public struct fat_arch { 49 | public var cputype: cpu_type_t /* cpu specifier (int) */ 50 | public var cpusubtype: cpu_subtype_t /* machine specifier (int) */ 51 | public var offset: UInt32 /* file offset to this object file */ 52 | public var size: UInt32 /* size of this object file */ 53 | public var align: UInt32 /* alignment as a power of 2 */ 54 | } 55 | 56 | struct load_command { 57 | var cmd: UInt32 58 | var cmdsize: UInt32 59 | } 60 | 61 | enum LoadCommands: UInt32 { 62 | case segment32 = 0x1 63 | case segment64 = 0x19 64 | case encryptionInfo32 = 0x21 65 | case encryptionInfo64 = 0x2C 66 | case codesignDirectives = 0x2B 67 | } 68 | 69 | struct symtab_command { 70 | var cmd: UInt32 /* LC_SYMTAB */ 71 | var cmdsize: UInt32 /* sizeof(struct symtab_command) */ 72 | var symoff: UInt32 /* symbol table offset */ 73 | var nsyms: UInt32 /* number of symbol table entries */ 74 | var stroff: UInt32 /* string table offset */ 75 | var strsize: UInt32 /* string table size in bytes */ 76 | } 77 | 78 | public struct segment_command { 79 | public var cmd: UInt32 /* for 32-bit architectures */ /* LC_SEGMENT */ 80 | public var cmdsize: UInt32 /* includes sizeof section structs */ 81 | public var segname: (Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8) /* segment name */ 82 | public var vmaddr: UInt32 /* memory address of this segment */ 83 | public var vmsize: UInt32 /* memory size of this segment */ 84 | public var fileoff: UInt32 /* file offset of this segment */ 85 | public var filesize: UInt32 /* amount to map from the file */ 86 | public var maxprot: vm_prot_t /* maximum VM protection */ 87 | public var initprot: vm_prot_t /* initial VM protection */ 88 | public var nsects: UInt32 /* number of sections in segment */ 89 | public var flags: UInt32 /* flags */ 90 | } 91 | 92 | public struct segment_command_64 { 93 | public var cmd: UInt32 /* for 64-bit architectures */ /* LC_SEGMENT_64 */ 94 | public var cmdsize: UInt32 /* includes sizeof section_64 structs */ 95 | public var segname: (Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8, Int8) /* segment name */ 96 | public var vmaddr: UInt64 /* memory address of this segment */ 97 | public var vmsize: UInt64 /* memory size of this segment */ 98 | public var fileoff: UInt64 /* file offset of this segment */ 99 | public var filesize: UInt64 /* amount to map from the file */ 100 | public var maxprot: vm_prot_t /* maximum VM protection */ 101 | public var initprot: vm_prot_t /* initial VM protection */ 102 | public var nsects: UInt32 /* number of sections in segment */ 103 | public var flags: UInt32 /* flags */ 104 | } 105 | 106 | struct encryption_info_command_32 { 107 | var cmd: UInt32 /* LC_ENCRYPTION_INFO */ 108 | var cmdsize: UInt32 /* sizeof(struct encryption_info_command_64) */ 109 | var cryptoff: UInt32 /* file offset of encrypted range */ 110 | var cryptsize: UInt32 /* file size of encrypted range */ 111 | var cryptid: UInt32 /* which enryption system, 0 means not-encrypted yet */ 112 | } 113 | 114 | // LC_ENCRYPTION_INFO_64 115 | struct encryption_info_command_64 { 116 | var cmd: UInt32 /* LC_ENCRYPTION_INFO */ 117 | var cmdsize: UInt32 /* sizeof(struct encryption_info_command) */ 118 | var cryptoff: UInt32 /* file offset of encrypted range */ 119 | var cryptsize: UInt32 /* file size of encrypted range */ 120 | var cryptid: UInt32 /* which enryption system, 0 means not-encrypted yet */ 121 | var pad: UInt32 /* padding to make this struct's size a multiple of 8 bytes */ 122 | } 123 | } 124 | -------------------------------------------------------------------------------- /Source/flexdecrypt.entitlements: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | application-identifier 6 | - 7 | com.apple.developer.team-identifier 8 | - 9 | com.apple.diagnosticd.diagnostic 10 | 11 | com.apple.frontboard.debugapplications 12 | 13 | com.apple.multitasking.termination 14 | 15 | com.apple.private.cs.debugger 16 | 17 | com.apple.private.security.no-sandbox 18 | 19 | com.apple.private.skip-library-validation 20 | 21 | com.apple.springboard.launchapplications 22 | 23 | dynamic-codesigning 24 | 25 | get-task-allow 26 | 27 | platform-application 28 | 29 | task_for_pid-allow 30 | 31 | 32 | 33 | -------------------------------------------------------------------------------- /Source/main.swift: -------------------------------------------------------------------------------- 1 | // 2 | // main.swift 3 | // Created on 6/30/20 4 | // 5 | 6 | import Foundation 7 | 8 | func disablePrintBuffering() { 9 | setbuf(__stdoutp, nil) 10 | } 11 | 12 | disablePrintBuffering() 13 | FlexDecrypt.main() 14 | -------------------------------------------------------------------------------- /flexdecrypt.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 52; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | FA8FFD3D24ABB7D0008FD73C /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = FA8FFD3C24ABB7D0008FD73C /* Assets.xcassets */; }; 11 | FA8FFD4024ABB7D0008FD73C /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = FA8FFD3E24ABB7D0008FD73C /* LaunchScreen.storyboard */; }; 12 | FA8FFD4B24ABBDB0008FD73C /* ArgumentParser in Frameworks */ = {isa = PBXBuildFile; productRef = FA8FFD4A24ABBDB0008FD73C /* ArgumentParser */; }; 13 | FA8FFD4D24ABBE14008FD73C /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD4C24ABBE14008FD73C /* main.swift */; }; 14 | FA8FFD5024ABBE9C008FD73C /* MachOFile.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD4F24ABBE9C008FD73C /* MachOFile.swift */; }; 15 | FA8FFD5224ABBEB8008FD73C /* MachOError.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5124ABBEB8008FD73C /* MachOError.swift */; }; 16 | FA8FFD5524ABBF10008FD73C /* FLXLog.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5424ABBF10008FD73C /* FLXLog.swift */; }; 17 | FA8FFD5724ABBFA0008FD73C /* MachOSlice.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5624ABBFA0008FD73C /* MachOSlice.swift */; }; 18 | FA8FFD5924ABBFB0008FD73C /* MachOBinary.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5824ABBFB0008FD73C /* MachOBinary.swift */; }; 19 | FA8FFD5B24ABC02C008FD73C /* MachOEncryptionInfo.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5A24ABC02C008FD73C /* MachOEncryptionInfo.swift */; }; 20 | FA8FFD6024ABC05B008FD73C /* FLXSystemApi.m in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD5E24ABC05B008FD73C /* FLXSystemApi.m */; }; 21 | FA8FFD6324ABC09E008FD73C /* FLXPrivateApi.mm in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6224ABC09E008FD73C /* FLXPrivateApi.mm */; }; 22 | FA8FFD6524ABC0BE008FD73C /* ArchitectureValue.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6424ABC0BE008FD73C /* ArchitectureValue.swift */; }; 23 | FA8FFD6724ABC0D1008FD73C /* MachOStructs.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6624ABC0D1008FD73C /* MachOStructs.swift */; }; 24 | FA8FFD6C24ABC0F5008FD73C /* DataConvertible.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6924ABC0F4008FD73C /* DataConvertible.swift */; }; 25 | FA8FFD6D24ABC0F5008FD73C /* DataView.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6A24ABC0F5008FD73C /* DataView.swift */; }; 26 | FA8FFD6E24ABC0F5008FD73C /* BinaryError.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6B24ABC0F5008FD73C /* BinaryError.swift */; }; 27 | FA8FFD7024ABC116008FD73C /* MachOHeader+DataConvertible.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD6F24ABC116008FD73C /* MachOHeader+DataConvertible.swift */; }; 28 | FA8FFD7224ABC130008FD73C /* MachOHeader.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD7124ABC130008FD73C /* MachOHeader.swift */; }; 29 | FA8FFD7424ABC141008FD73C /* MachOLoadCommand.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD7324ABC141008FD73C /* MachOLoadCommand.swift */; }; 30 | FA8FFD7A24ABC18D008FD73C /* MachOSegment.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD7924ABC18D008FD73C /* MachOSegment.swift */; }; 31 | FA8FFD7D24ABDC08008FD73C /* MachOFile+SpawnDecrypt.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD7C24ABDC08008FD73C /* MachOFile+SpawnDecrypt.swift */; }; 32 | FA8FFD8024ABDC4B008FD73C /* Int+Convenience.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD7F24ABDC4B008FD73C /* Int+Convenience.swift */; }; 33 | FA8FFD8224ABE516008FD73C /* MachOFile+Decrypt.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD8124ABE516008FD73C /* MachOFile+Decrypt.swift */; }; 34 | FA8FFD8524AC133E008FD73C /* DecryptFile.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD8424AC133E008FD73C /* DecryptFile.swift */; }; 35 | FA8FFD8824AC165C008FD73C /* FlexDecrypt.swift in Sources */ = {isa = PBXBuildFile; fileRef = FA8FFD8724AC165C008FD73C /* FlexDecrypt.swift */; }; 36 | FA98596524ACE4DF003D19EB /* control in Resources */ = {isa = PBXBuildFile; fileRef = FA98596324ACE4DF003D19EB /* control */; }; 37 | /* End PBXBuildFile section */ 38 | 39 | /* Begin PBXFileReference section */ 40 | FA8FFD3024ABB7CB008FD73C /* flexdecrypt.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = flexdecrypt.app; sourceTree = BUILT_PRODUCTS_DIR; }; 41 | FA8FFD3C24ABB7D0008FD73C /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 42 | FA8FFD3F24ABB7D0008FD73C /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 43 | FA8FFD4124ABB7D0008FD73C /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 44 | FA8FFD4724ABB96A008FD73C /* flexdecrypt.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; name = flexdecrypt.entitlements; path = Source/flexdecrypt.entitlements; sourceTree = SOURCE_ROOT; }; 45 | FA8FFD4C24ABBE14008FD73C /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = ""; }; 46 | FA8FFD4F24ABBE9C008FD73C /* MachOFile.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MachOFile.swift; sourceTree = ""; }; 47 | FA8FFD5124ABBEB8008FD73C /* MachOError.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MachOError.swift; sourceTree = ""; }; 48 | FA8FFD5424ABBF10008FD73C /* FLXLog.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FLXLog.swift; sourceTree = ""; }; 49 | FA8FFD5624ABBFA0008FD73C /* MachOSlice.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOSlice.swift; sourceTree = ""; }; 50 | FA8FFD5824ABBFB0008FD73C /* MachOBinary.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOBinary.swift; sourceTree = ""; }; 51 | FA8FFD5A24ABC02C008FD73C /* MachOEncryptionInfo.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOEncryptionInfo.swift; sourceTree = ""; }; 52 | FA8FFD5D24ABC05A008FD73C /* Bridging.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = Bridging.h; sourceTree = ""; }; 53 | FA8FFD5E24ABC05B008FD73C /* FLXSystemApi.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = FLXSystemApi.m; sourceTree = ""; }; 54 | FA8FFD5F24ABC05B008FD73C /* FLXSystemApi.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = FLXSystemApi.h; sourceTree = ""; }; 55 | FA8FFD6124ABC09E008FD73C /* FLXPrivateApi.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = FLXPrivateApi.h; sourceTree = ""; }; 56 | FA8FFD6224ABC09E008FD73C /* FLXPrivateApi.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = FLXPrivateApi.mm; sourceTree = ""; }; 57 | FA8FFD6424ABC0BE008FD73C /* ArchitectureValue.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ArchitectureValue.swift; sourceTree = ""; }; 58 | FA8FFD6624ABC0D1008FD73C /* MachOStructs.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOStructs.swift; sourceTree = ""; }; 59 | FA8FFD6924ABC0F4008FD73C /* DataConvertible.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DataConvertible.swift; sourceTree = ""; }; 60 | FA8FFD6A24ABC0F5008FD73C /* DataView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DataView.swift; sourceTree = ""; }; 61 | FA8FFD6B24ABC0F5008FD73C /* BinaryError.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BinaryError.swift; sourceTree = ""; }; 62 | FA8FFD6F24ABC116008FD73C /* MachOHeader+DataConvertible.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "MachOHeader+DataConvertible.swift"; sourceTree = ""; }; 63 | FA8FFD7124ABC130008FD73C /* MachOHeader.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOHeader.swift; sourceTree = ""; }; 64 | FA8FFD7324ABC141008FD73C /* MachOLoadCommand.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOLoadCommand.swift; sourceTree = ""; }; 65 | FA8FFD7924ABC18D008FD73C /* MachOSegment.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MachOSegment.swift; sourceTree = ""; }; 66 | FA8FFD7C24ABDC08008FD73C /* MachOFile+SpawnDecrypt.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "MachOFile+SpawnDecrypt.swift"; sourceTree = ""; }; 67 | FA8FFD7F24ABDC4B008FD73C /* Int+Convenience.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "Int+Convenience.swift"; sourceTree = ""; }; 68 | FA8FFD8124ABE516008FD73C /* MachOFile+Decrypt.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "MachOFile+Decrypt.swift"; sourceTree = ""; }; 69 | FA8FFD8424AC133E008FD73C /* DecryptFile.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DecryptFile.swift; sourceTree = ""; }; 70 | FA8FFD8724AC165C008FD73C /* FlexDecrypt.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FlexDecrypt.swift; sourceTree = ""; }; 71 | FA98596324ACE4DF003D19EB /* control */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = control; sourceTree = ""; }; 72 | /* End PBXFileReference section */ 73 | 74 | /* Begin PBXFrameworksBuildPhase section */ 75 | FA8FFD2D24ABB7CB008FD73C /* Frameworks */ = { 76 | isa = PBXFrameworksBuildPhase; 77 | buildActionMask = 2147483647; 78 | files = ( 79 | FA8FFD4B24ABBDB0008FD73C /* ArgumentParser in Frameworks */, 80 | ); 81 | runOnlyForDeploymentPostprocessing = 0; 82 | }; 83 | /* End PBXFrameworksBuildPhase section */ 84 | 85 | /* Begin PBXGroup section */ 86 | FA8FFD2724ABB7CB008FD73C = { 87 | isa = PBXGroup; 88 | children = ( 89 | FA8FFD8624AC1642008FD73C /* Source */, 90 | FA98595E24ACE4DF003D19EB /* Package */, 91 | FA8FFD8924AC16A2008FD73C /* App Resources */, 92 | FA8FFD3124ABB7CB008FD73C /* Products */, 93 | ); 94 | sourceTree = ""; 95 | }; 96 | FA8FFD3124ABB7CB008FD73C /* Products */ = { 97 | isa = PBXGroup; 98 | children = ( 99 | FA8FFD3024ABB7CB008FD73C /* flexdecrypt.app */, 100 | ); 101 | name = Products; 102 | sourceTree = ""; 103 | }; 104 | FA8FFD4E24ABBE8E008FD73C /* Mach-O */ = { 105 | isa = PBXGroup; 106 | children = ( 107 | FA8FFD8A24AC18C1008FD73C /* Structure */, 108 | FA8FFD7B24ABDC00008FD73C /* Decrypt */, 109 | FA8FFD4F24ABBE9C008FD73C /* MachOFile.swift */, 110 | FA8FFD5624ABBFA0008FD73C /* MachOSlice.swift */, 111 | FA8FFD5124ABBEB8008FD73C /* MachOError.swift */, 112 | FA8FFD5824ABBFB0008FD73C /* MachOBinary.swift */, 113 | ); 114 | path = "Mach-O"; 115 | sourceTree = ""; 116 | }; 117 | FA8FFD5324ABBF06008FD73C /* Debugging */ = { 118 | isa = PBXGroup; 119 | children = ( 120 | FA8FFD5424ABBF10008FD73C /* FLXLog.swift */, 121 | ); 122 | path = Debugging; 123 | sourceTree = ""; 124 | }; 125 | FA8FFD5C24ABC050008FD73C /* C API Wrappers */ = { 126 | isa = PBXGroup; 127 | children = ( 128 | FA8FFD5F24ABC05B008FD73C /* FLXSystemApi.h */, 129 | FA8FFD5E24ABC05B008FD73C /* FLXSystemApi.m */, 130 | FA8FFD6124ABC09E008FD73C /* FLXPrivateApi.h */, 131 | FA8FFD6224ABC09E008FD73C /* FLXPrivateApi.mm */, 132 | ); 133 | path = "C API Wrappers"; 134 | sourceTree = ""; 135 | }; 136 | FA8FFD6824ABC0E9008FD73C /* Binary Reading */ = { 137 | isa = PBXGroup; 138 | children = ( 139 | FA8FFD6B24ABC0F5008FD73C /* BinaryError.swift */, 140 | FA8FFD6924ABC0F4008FD73C /* DataConvertible.swift */, 141 | FA8FFD6A24ABC0F5008FD73C /* DataView.swift */, 142 | ); 143 | path = "Binary Reading"; 144 | sourceTree = ""; 145 | }; 146 | FA8FFD7B24ABDC00008FD73C /* Decrypt */ = { 147 | isa = PBXGroup; 148 | children = ( 149 | FA8FFD7C24ABDC08008FD73C /* MachOFile+SpawnDecrypt.swift */, 150 | FA8FFD8124ABE516008FD73C /* MachOFile+Decrypt.swift */, 151 | ); 152 | path = Decrypt; 153 | sourceTree = ""; 154 | }; 155 | FA8FFD7E24ABDC42008FD73C /* Extensions */ = { 156 | isa = PBXGroup; 157 | children = ( 158 | FA8FFD7F24ABDC4B008FD73C /* Int+Convenience.swift */, 159 | ); 160 | path = Extensions; 161 | sourceTree = ""; 162 | }; 163 | FA8FFD8324AC1332008FD73C /* Commands */ = { 164 | isa = PBXGroup; 165 | children = ( 166 | FA8FFD8724AC165C008FD73C /* FlexDecrypt.swift */, 167 | FA8FFD8424AC133E008FD73C /* DecryptFile.swift */, 168 | ); 169 | path = Commands; 170 | sourceTree = ""; 171 | }; 172 | FA8FFD8624AC1642008FD73C /* Source */ = { 173 | isa = PBXGroup; 174 | children = ( 175 | FA8FFD4C24ABBE14008FD73C /* main.swift */, 176 | FA8FFD8324AC1332008FD73C /* Commands */, 177 | FA8FFD4E24ABBE8E008FD73C /* Mach-O */, 178 | FA8FFD6824ABC0E9008FD73C /* Binary Reading */, 179 | FA8FFD7E24ABDC42008FD73C /* Extensions */, 180 | FA8FFD5C24ABC050008FD73C /* C API Wrappers */, 181 | FA8FFD5324ABBF06008FD73C /* Debugging */, 182 | FA8FFD5D24ABC05A008FD73C /* Bridging.h */, 183 | FA8FFD4724ABB96A008FD73C /* flexdecrypt.entitlements */, 184 | ); 185 | path = Source; 186 | sourceTree = ""; 187 | }; 188 | FA8FFD8924AC16A2008FD73C /* App Resources */ = { 189 | isa = PBXGroup; 190 | children = ( 191 | FA8FFD4124ABB7D0008FD73C /* Info.plist */, 192 | FA8FFD3C24ABB7D0008FD73C /* Assets.xcassets */, 193 | FA8FFD3E24ABB7D0008FD73C /* LaunchScreen.storyboard */, 194 | ); 195 | path = "App Resources"; 196 | sourceTree = ""; 197 | }; 198 | FA8FFD8A24AC18C1008FD73C /* Structure */ = { 199 | isa = PBXGroup; 200 | children = ( 201 | FA8FFD7124ABC130008FD73C /* MachOHeader.swift */, 202 | FA8FFD6F24ABC116008FD73C /* MachOHeader+DataConvertible.swift */, 203 | FA8FFD7324ABC141008FD73C /* MachOLoadCommand.swift */, 204 | FA8FFD7924ABC18D008FD73C /* MachOSegment.swift */, 205 | FA8FFD6624ABC0D1008FD73C /* MachOStructs.swift */, 206 | FA8FFD6424ABC0BE008FD73C /* ArchitectureValue.swift */, 207 | FA8FFD5A24ABC02C008FD73C /* MachOEncryptionInfo.swift */, 208 | ); 209 | path = Structure; 210 | sourceTree = ""; 211 | }; 212 | FA98595E24ACE4DF003D19EB /* Package */ = { 213 | isa = PBXGroup; 214 | children = ( 215 | FA98596224ACE4DF003D19EB /* DEBIAN */, 216 | ); 217 | path = Package; 218 | sourceTree = ""; 219 | }; 220 | FA98596224ACE4DF003D19EB /* DEBIAN */ = { 221 | isa = PBXGroup; 222 | children = ( 223 | FA98596324ACE4DF003D19EB /* control */, 224 | ); 225 | path = DEBIAN; 226 | sourceTree = ""; 227 | }; 228 | /* End PBXGroup section */ 229 | 230 | /* Begin PBXNativeTarget section */ 231 | FA8FFD2F24ABB7CB008FD73C /* flexdecrypt */ = { 232 | isa = PBXNativeTarget; 233 | buildConfigurationList = FA8FFD4424ABB7D0008FD73C /* Build configuration list for PBXNativeTarget "flexdecrypt" */; 234 | buildPhases = ( 235 | FA8FFD2C24ABB7CB008FD73C /* Sources */, 236 | FA8FFD2D24ABB7CB008FD73C /* Frameworks */, 237 | FA8FFD2E24ABB7CB008FD73C /* Resources */, 238 | FA8FFD4824ABB974008FD73C /* Codesign */, 239 | ); 240 | buildRules = ( 241 | ); 242 | dependencies = ( 243 | ); 244 | name = flexdecrypt; 245 | packageProductDependencies = ( 246 | FA8FFD4A24ABBDB0008FD73C /* ArgumentParser */, 247 | ); 248 | productName = flexdecrypt; 249 | productReference = FA8FFD3024ABB7CB008FD73C /* flexdecrypt.app */; 250 | productType = "com.apple.product-type.application"; 251 | }; 252 | /* End PBXNativeTarget section */ 253 | 254 | /* Begin PBXProject section */ 255 | FA8FFD2824ABB7CB008FD73C /* Project object */ = { 256 | isa = PBXProject; 257 | attributes = { 258 | LastSwiftUpdateCheck = 1150; 259 | LastUpgradeCheck = 1150; 260 | ORGANIZATIONNAME = "John Coates"; 261 | TargetAttributes = { 262 | FA8FFD2F24ABB7CB008FD73C = { 263 | CreatedOnToolsVersion = 11.5; 264 | LastSwiftMigration = 1150; 265 | }; 266 | }; 267 | }; 268 | buildConfigurationList = FA8FFD2B24ABB7CB008FD73C /* Build configuration list for PBXProject "flexdecrypt" */; 269 | compatibilityVersion = "Xcode 9.3"; 270 | developmentRegion = en; 271 | hasScannedForEncodings = 0; 272 | knownRegions = ( 273 | en, 274 | Base, 275 | ); 276 | mainGroup = FA8FFD2724ABB7CB008FD73C; 277 | packageReferences = ( 278 | FA8FFD4924ABBDB0008FD73C /* XCRemoteSwiftPackageReference "swift-argument-parser" */, 279 | ); 280 | productRefGroup = FA8FFD3124ABB7CB008FD73C /* Products */; 281 | projectDirPath = ""; 282 | projectRoot = ""; 283 | targets = ( 284 | FA8FFD2F24ABB7CB008FD73C /* flexdecrypt */, 285 | ); 286 | }; 287 | /* End PBXProject section */ 288 | 289 | /* Begin PBXResourcesBuildPhase section */ 290 | FA8FFD2E24ABB7CB008FD73C /* Resources */ = { 291 | isa = PBXResourcesBuildPhase; 292 | buildActionMask = 2147483647; 293 | files = ( 294 | FA98596524ACE4DF003D19EB /* control in Resources */, 295 | FA8FFD4024ABB7D0008FD73C /* LaunchScreen.storyboard in Resources */, 296 | FA8FFD3D24ABB7D0008FD73C /* Assets.xcassets in Resources */, 297 | ); 298 | runOnlyForDeploymentPostprocessing = 0; 299 | }; 300 | /* End PBXResourcesBuildPhase section */ 301 | 302 | /* Begin PBXShellScriptBuildPhase section */ 303 | FA8FFD4824ABB974008FD73C /* Codesign */ = { 304 | isa = PBXShellScriptBuildPhase; 305 | buildActionMask = 2147483647; 306 | files = ( 307 | ); 308 | inputFileListPaths = ( 309 | ); 310 | inputPaths = ( 311 | ); 312 | name = Codesign; 313 | outputFileListPaths = ( 314 | ); 315 | outputPaths = ( 316 | ); 317 | runOnlyForDeploymentPostprocessing = 0; 318 | shellPath = /bin/sh; 319 | shellScript = "set -x\nset -e\nexport appPath=$CODESIGNING_FOLDER_PATH\nexport binaryPath=$appPath/$PRODUCT_NAME\nexport entitlementsPath=$CODE_SIGN_ENTITLEMENTS\nexport plistBuddy=/usr/libexec/PlistBuddy\n\nif [ $PLATFORM_NAME = \"iphoneos\" ] && [ $CONFIGURATION = \"Debug\" ]; then\n echo \"warning: Entitling binary\"\n pushd ~/Library/MobileDevice/Provisioning\\ Profiles/\n FILES=./*\n for file in $FILES\n do\n echo \"Reading $file\"\n found=0\n security cms -D -i $file > /tmp/profile.plist \n wildcardAppId=\"Xcode: Wildcard AppID\"\n currentAppId=$($plistBuddy -c \"Print :AppIDName\" /tmp/profile.plist)\n if [[ \"$currentAppId\" == \"$wildcardAppId\" ]]; then\n currentAppId=$($plistBuddy -c \"Print :AppIDName\" /tmp/profile.plist) \n ApplicationIdentifierPrefix=$($plistBuddy -c \"Print :ApplicationIdentifierPrefix:0\" /tmp/profile.plist)\n TeamIdentifier=$($plistBuddy -c \"Print :TeamIdentifier:0\" /tmp/profile.plist)\n TeamName=$($plistBuddy -c \"Print :TeamName\" /tmp/profile.plist)\n echo \"Found Wildcard Provisoning Profile\"\n echo \"ApplicationIdentifierPrefix: $ApplicationIdentifierPrefix\"\n echo \"TeamIdentifier: $TeamIdentifier\"\n echo \"TeamName: $TeamName\"\n found=1\n rm /tmp/profile.plist\n break\n fi\n \n rm /tmp/profile.plist\n \n if [[ found == 0 ]]; then\n echo \"Error: Unable to find wildcard provisioning profile!\"\n exit 1\n fi\n done\n popd\n\n $plistBuddy -c \"Set :application-identifier $ApplicationIdentifierPrefix.$PRODUCT_BUNDLE_IDENTIFIER\" \"$entitlementsPath\"\n $plistBuddy -c \"Set :com.apple.developer.team-identifier $TeamIdentifier\" \"$entitlementsPath\"\n\n codesignIdentity=\"Apple Development: $TeamName\"\n FRAMEWORKS_DIR=\"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}\"\n find \"${FRAMEWORKS_DIR}\" -perm +111 -type f -exec codesign -fs \"$codesignIdentity\" \"{}\" \\;\n find \"${FRAMEWORKS_DIR}\" -perm +111 -type f -exec codesign -d \"$codesignIdentity\" \"{}\" \\;\n\n codesign --deep -fs \"$codesignIdentity\" --entitlements \"${entitlementsPath}\" \"${appPath}\"\n \n returnValue=$?\n \n codesign -d \"$appPath\"\n \n # clear\n $plistBuddy -c \"Set :application-identifier -\" \"$entitlementsPath\"\n $plistBuddy -c \"Set :com.apple.developer.team-identifier -\" \"$entitlementsPath\"\n \n if [[ $returnValue != 0 ]]; then\n exit $returnValue;\n fi\nelif [ $PLATFORM_NAME = \"iphoneos\" ] && [ $CONFIGURATION = \"Release\" ]; then\n echo \"warning: adhoc codesigning\"\n export entitlementsPath=$CODE_SIGN_ENTITLEMENTS\n export newEntitlementsPath=\"$CONFIGURATION_BUILD_DIR/modified.entitlements\"\n cp \"$entitlementsPath\" \"$newEntitlementsPath\"\n $plistBuddy -c \"Remove :application-identifier\" \"$newEntitlementsPath\"\n $plistBuddy -c \"Remove :com.apple.developer.team-identifier\" \"$newEntitlementsPath\"\n codesign --deep -f -s - --entitlements \"${newEntitlementsPath}\" \"${appPath}\"\n codesign -d \"$appPath\"\nfi\n"; 320 | }; 321 | /* End PBXShellScriptBuildPhase section */ 322 | 323 | /* Begin PBXSourcesBuildPhase section */ 324 | FA8FFD2C24ABB7CB008FD73C /* Sources */ = { 325 | isa = PBXSourcesBuildPhase; 326 | buildActionMask = 2147483647; 327 | files = ( 328 | FA8FFD5724ABBFA0008FD73C /* MachOSlice.swift in Sources */, 329 | FA8FFD5524ABBF10008FD73C /* FLXLog.swift in Sources */, 330 | FA8FFD6024ABC05B008FD73C /* FLXSystemApi.m in Sources */, 331 | FA8FFD5B24ABC02C008FD73C /* MachOEncryptionInfo.swift in Sources */, 332 | FA8FFD6C24ABC0F5008FD73C /* DataConvertible.swift in Sources */, 333 | FA8FFD8524AC133E008FD73C /* DecryptFile.swift in Sources */, 334 | FA8FFD7D24ABDC08008FD73C /* MachOFile+SpawnDecrypt.swift in Sources */, 335 | FA8FFD6324ABC09E008FD73C /* FLXPrivateApi.mm in Sources */, 336 | FA8FFD5224ABBEB8008FD73C /* MachOError.swift in Sources */, 337 | FA8FFD7424ABC141008FD73C /* MachOLoadCommand.swift in Sources */, 338 | FA8FFD8824AC165C008FD73C /* FlexDecrypt.swift in Sources */, 339 | FA8FFD8024ABDC4B008FD73C /* Int+Convenience.swift in Sources */, 340 | FA8FFD4D24ABBE14008FD73C /* main.swift in Sources */, 341 | FA8FFD5924ABBFB0008FD73C /* MachOBinary.swift in Sources */, 342 | FA8FFD7A24ABC18D008FD73C /* MachOSegment.swift in Sources */, 343 | FA8FFD6D24ABC0F5008FD73C /* DataView.swift in Sources */, 344 | FA8FFD6724ABC0D1008FD73C /* MachOStructs.swift in Sources */, 345 | FA8FFD8224ABE516008FD73C /* MachOFile+Decrypt.swift in Sources */, 346 | FA8FFD7224ABC130008FD73C /* MachOHeader.swift in Sources */, 347 | FA8FFD6524ABC0BE008FD73C /* ArchitectureValue.swift in Sources */, 348 | FA8FFD7024ABC116008FD73C /* MachOHeader+DataConvertible.swift in Sources */, 349 | FA8FFD6E24ABC0F5008FD73C /* BinaryError.swift in Sources */, 350 | FA8FFD5024ABBE9C008FD73C /* MachOFile.swift in Sources */, 351 | ); 352 | runOnlyForDeploymentPostprocessing = 0; 353 | }; 354 | /* End PBXSourcesBuildPhase section */ 355 | 356 | /* Begin PBXVariantGroup section */ 357 | FA8FFD3E24ABB7D0008FD73C /* LaunchScreen.storyboard */ = { 358 | isa = PBXVariantGroup; 359 | children = ( 360 | FA8FFD3F24ABB7D0008FD73C /* Base */, 361 | ); 362 | name = LaunchScreen.storyboard; 363 | sourceTree = ""; 364 | }; 365 | /* End PBXVariantGroup section */ 366 | 367 | /* Begin XCBuildConfiguration section */ 368 | FA8FFD4224ABB7D0008FD73C /* Debug */ = { 369 | isa = XCBuildConfiguration; 370 | buildSettings = { 371 | ALWAYS_SEARCH_USER_PATHS = NO; 372 | CLANG_ANALYZER_NONNULL = YES; 373 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 374 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 375 | CLANG_CXX_LIBRARY = "libc++"; 376 | CLANG_ENABLE_MODULES = YES; 377 | CLANG_ENABLE_OBJC_ARC = YES; 378 | CLANG_ENABLE_OBJC_WEAK = YES; 379 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 380 | CLANG_WARN_BOOL_CONVERSION = YES; 381 | CLANG_WARN_COMMA = YES; 382 | CLANG_WARN_CONSTANT_CONVERSION = YES; 383 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 384 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 385 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 386 | CLANG_WARN_EMPTY_BODY = YES; 387 | CLANG_WARN_ENUM_CONVERSION = YES; 388 | CLANG_WARN_INFINITE_RECURSION = YES; 389 | CLANG_WARN_INT_CONVERSION = YES; 390 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 391 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 392 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 393 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 394 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 395 | CLANG_WARN_STRICT_PROTOTYPES = YES; 396 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 397 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 398 | CLANG_WARN_UNREACHABLE_CODE = YES; 399 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 400 | COPY_PHASE_STRIP = NO; 401 | DEBUG_INFORMATION_FORMAT = dwarf; 402 | ENABLE_STRICT_OBJC_MSGSEND = YES; 403 | ENABLE_TESTABILITY = YES; 404 | GCC_C_LANGUAGE_STANDARD = gnu11; 405 | GCC_DYNAMIC_NO_PIC = NO; 406 | GCC_NO_COMMON_BLOCKS = YES; 407 | GCC_OPTIMIZATION_LEVEL = 0; 408 | GCC_PREPROCESSOR_DEFINITIONS = ( 409 | "DEBUG=1", 410 | "$(inherited)", 411 | ); 412 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 413 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 414 | GCC_WARN_UNDECLARED_SELECTOR = YES; 415 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 416 | GCC_WARN_UNUSED_FUNCTION = YES; 417 | GCC_WARN_UNUSED_VARIABLE = YES; 418 | IPHONEOS_DEPLOYMENT_TARGET = 9.0; 419 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 420 | MTL_FAST_MATH = YES; 421 | ONLY_ACTIVE_ARCH = YES; 422 | SDKROOT = iphoneos; 423 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 424 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 425 | }; 426 | name = Debug; 427 | }; 428 | FA8FFD4324ABB7D0008FD73C /* Release */ = { 429 | isa = XCBuildConfiguration; 430 | buildSettings = { 431 | ALWAYS_SEARCH_USER_PATHS = NO; 432 | CLANG_ANALYZER_NONNULL = YES; 433 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 434 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 435 | CLANG_CXX_LIBRARY = "libc++"; 436 | CLANG_ENABLE_MODULES = YES; 437 | CLANG_ENABLE_OBJC_ARC = YES; 438 | CLANG_ENABLE_OBJC_WEAK = YES; 439 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 440 | CLANG_WARN_BOOL_CONVERSION = YES; 441 | CLANG_WARN_COMMA = YES; 442 | CLANG_WARN_CONSTANT_CONVERSION = YES; 443 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 444 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 445 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 446 | CLANG_WARN_EMPTY_BODY = YES; 447 | CLANG_WARN_ENUM_CONVERSION = YES; 448 | CLANG_WARN_INFINITE_RECURSION = YES; 449 | CLANG_WARN_INT_CONVERSION = YES; 450 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 451 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 452 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 453 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 454 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 455 | CLANG_WARN_STRICT_PROTOTYPES = YES; 456 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 457 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 458 | CLANG_WARN_UNREACHABLE_CODE = YES; 459 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 460 | COPY_PHASE_STRIP = NO; 461 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 462 | ENABLE_NS_ASSERTIONS = NO; 463 | ENABLE_STRICT_OBJC_MSGSEND = YES; 464 | GCC_C_LANGUAGE_STANDARD = gnu11; 465 | GCC_NO_COMMON_BLOCKS = YES; 466 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 467 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 468 | GCC_WARN_UNDECLARED_SELECTOR = YES; 469 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 470 | GCC_WARN_UNUSED_FUNCTION = YES; 471 | GCC_WARN_UNUSED_VARIABLE = YES; 472 | IPHONEOS_DEPLOYMENT_TARGET = 9.0; 473 | MTL_ENABLE_DEBUG_INFO = NO; 474 | MTL_FAST_MATH = YES; 475 | SDKROOT = iphoneos; 476 | SWIFT_COMPILATION_MODE = wholemodule; 477 | SWIFT_OPTIMIZATION_LEVEL = "-O"; 478 | VALIDATE_PRODUCT = YES; 479 | }; 480 | name = Release; 481 | }; 482 | FA8FFD4524ABB7D0008FD73C /* Debug */ = { 483 | isa = XCBuildConfiguration; 484 | buildSettings = { 485 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 486 | CLANG_ENABLE_MODULES = YES; 487 | CODE_SIGNING_ALLOWED = NO; 488 | CODE_SIGNING_REQUIRED = NO; 489 | CODE_SIGN_ENTITLEMENTS = $PROJECT_DIR/Source/flexdecrypt.entitlements; 490 | CODE_SIGN_STYLE = Manual; 491 | DEVELOPMENT_TEAM = ""; 492 | INFOPLIST_FILE = "App Resources/Info.plist"; 493 | IPHONEOS_DEPLOYMENT_TARGET = 9.0; 494 | LD_RUNPATH_SEARCH_PATHS = ( 495 | "$(inherited)", 496 | "@executable_path/Frameworks", 497 | /usr/lib/libswift/stable, 498 | ); 499 | MARKETING_VERSION = 1.1; 500 | PRODUCT_BUNDLE_IDENTIFIER = com.johncoates.flexdecrypt; 501 | PRODUCT_NAME = "$(TARGET_NAME)"; 502 | PROVISIONING_PROFILE_SPECIFIER = ""; 503 | SWIFT_OBJC_BRIDGING_HEADER = $PROJECT_DIR/Source/Bridging.h; 504 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 505 | SWIFT_VERSION = 5.0; 506 | SYSTEM_HEADER_SEARCH_PATHS = $PROJECT_DIR/External/include; 507 | TARGETED_DEVICE_FAMILY = "1,2"; 508 | }; 509 | name = Debug; 510 | }; 511 | FA8FFD4624ABB7D0008FD73C /* Release */ = { 512 | isa = XCBuildConfiguration; 513 | buildSettings = { 514 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 515 | CLANG_ENABLE_MODULES = YES; 516 | CODE_SIGNING_ALLOWED = NO; 517 | CODE_SIGNING_REQUIRED = NO; 518 | CODE_SIGN_ENTITLEMENTS = $PROJECT_DIR/Source/flexdecrypt.entitlements; 519 | CODE_SIGN_STYLE = Manual; 520 | DEVELOPMENT_TEAM = ""; 521 | INFOPLIST_FILE = "App Resources/Info.plist"; 522 | IPHONEOS_DEPLOYMENT_TARGET = 9.0; 523 | LD_RUNPATH_SEARCH_PATHS = ( 524 | "$(inherited)", 525 | "@executable_path/Frameworks", 526 | /usr/lib/libswift/stable, 527 | ); 528 | MARKETING_VERSION = 1.1; 529 | PRODUCT_BUNDLE_IDENTIFIER = com.johncoates.flexdecrypt; 530 | PRODUCT_NAME = "$(TARGET_NAME)"; 531 | PROVISIONING_PROFILE_SPECIFIER = ""; 532 | SWIFT_OBJC_BRIDGING_HEADER = $PROJECT_DIR/Source/Bridging.h; 533 | SWIFT_VERSION = 5.0; 534 | SYSTEM_HEADER_SEARCH_PATHS = $PROJECT_DIR/External/include; 535 | TARGETED_DEVICE_FAMILY = "1,2"; 536 | }; 537 | name = Release; 538 | }; 539 | /* End XCBuildConfiguration section */ 540 | 541 | /* Begin XCConfigurationList section */ 542 | FA8FFD2B24ABB7CB008FD73C /* Build configuration list for PBXProject "flexdecrypt" */ = { 543 | isa = XCConfigurationList; 544 | buildConfigurations = ( 545 | FA8FFD4224ABB7D0008FD73C /* Debug */, 546 | FA8FFD4324ABB7D0008FD73C /* Release */, 547 | ); 548 | defaultConfigurationIsVisible = 0; 549 | defaultConfigurationName = Release; 550 | }; 551 | FA8FFD4424ABB7D0008FD73C /* Build configuration list for PBXNativeTarget "flexdecrypt" */ = { 552 | isa = XCConfigurationList; 553 | buildConfigurations = ( 554 | FA8FFD4524ABB7D0008FD73C /* Debug */, 555 | FA8FFD4624ABB7D0008FD73C /* Release */, 556 | ); 557 | defaultConfigurationIsVisible = 0; 558 | defaultConfigurationName = Release; 559 | }; 560 | /* End XCConfigurationList section */ 561 | 562 | /* Begin XCRemoteSwiftPackageReference section */ 563 | FA8FFD4924ABBDB0008FD73C /* XCRemoteSwiftPackageReference "swift-argument-parser" */ = { 564 | isa = XCRemoteSwiftPackageReference; 565 | repositoryURL = "https://github.com/apple/swift-argument-parser"; 566 | requirement = { 567 | kind = upToNextMajorVersion; 568 | minimumVersion = 0.2.0; 569 | }; 570 | }; 571 | /* End XCRemoteSwiftPackageReference section */ 572 | 573 | /* Begin XCSwiftPackageProductDependency section */ 574 | FA8FFD4A24ABBDB0008FD73C /* ArgumentParser */ = { 575 | isa = XCSwiftPackageProductDependency; 576 | package = FA8FFD4924ABBDB0008FD73C /* XCRemoteSwiftPackageReference "swift-argument-parser" */; 577 | productName = ArgumentParser; 578 | }; 579 | /* End XCSwiftPackageProductDependency section */ 580 | }; 581 | rootObject = FA8FFD2824ABB7CB008FD73C /* Project object */; 582 | } 583 | -------------------------------------------------------------------------------- /flexdecrypt.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /flexdecrypt.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /flexdecrypt.xcodeproj/xcshareddata/xcschemes/flexdecrypt.xcscheme: -------------------------------------------------------------------------------- 1 | 2 | 5 | 8 | 9 | 15 | 21 | 22 | 23 | 24 | 25 | 30 | 31 | 32 | 33 | 43 | 45 | 51 | 52 | 53 | 54 | 57 | 58 | 59 | 60 | 66 | 68 | 74 | 75 | 76 | 77 | 79 | 80 | 83 | 84 | 85 | --------------------------------------------------------------------------------