ViewController.m 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243
  1. //
  2. // ViewController.m
  3. // g0blin
  4. //
  5. // Created by Sticktron on 2017-12-26.
  6. // Copyright © 2017 Sticktron. All rights reserved.
  7. //
  8. #import "ViewController.h"
  9. #import "SettingsController.h"
  10. #include "v0rtex.h"
  11. #include "common.h"
  12. #include "offsets.h"
  13. #include "kernel.h"
  14. #include "kpp.h"
  15. #include "remount.h"
  16. #include "bootstrap.h"
  17. #include <sys/utsname.h>
  18. #import <AVFoundation/AVFoundation.h>
  19. #import <AVKit/AVKit.h>
  20. #define GRAPE [UIColor colorWithRed:0.5 green:0 blue:1 alpha:1]
  21. @interface ViewController ()
  22. @property (weak, nonatomic) IBOutlet UIImageView *logoView;
  23. @property (weak, nonatomic) IBOutlet UIButton *goButton;
  24. @property (weak, nonatomic) IBOutlet UITextView *consoleView;
  25. @property (weak, nonatomic) IBOutlet UIButton *settingsButton;
  26. @property (weak, nonatomic) IBOutlet UILabel *reinstallBootstrapLabel;
  27. @end
  28. static task_t tfp0;
  29. static uint64_t kslide;
  30. static uint64_t kbase;
  31. static uint64_t kcred;
  32. BOOL respringNeeded;
  33. BOOL fun;
  34. AVPlayer *player;
  35. AVPlayerViewController *cont;
  36. @implementation ViewController
  37. - (void)viewDidLoad {
  38. [super viewDidLoad];
  39. // Do any additional setup after loading the view, typically from a nib.
  40. self.consoleView.layer.cornerRadius = 6;
  41. self.consoleView.text = nil;
  42. self.goButton.layer.cornerRadius = 16;
  43. self.reinstallBootstrapLabel.hidden = YES;
  44. // print kernel version
  45. struct utsname u;
  46. uname(&u);
  47. [self log:[NSString stringWithFormat:@"%s \n", u.version]];
  48. // abort if already jailbroken
  49. if (strstr(u.version, "MarijuanARM")) {
  50. self.goButton.enabled = NO;
  51. self.goButton.backgroundColor = UIColor.darkGrayColor;
  52. [self.goButton setTitle:@"jailbroke yo!" forState:UIControlStateDisabled];
  53. }
  54. // try to load offsets for device
  55. if (init_offsets() == KERN_SUCCESS) {
  56. [self log:@"Ready. \n"];
  57. } else {
  58. self.goButton.enabled = NO;
  59. self.goButton.backgroundColor = UIColor.darkGrayColor;
  60. [self.goButton setTitle:@"device not supported" forState:UIControlStateDisabled];
  61. }
  62. // fun
  63. UITapGestureRecognizer *doubleTap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(fun:)];
  64. doubleTap.delaysTouchesBegan = YES;
  65. doubleTap.numberOfTapsRequired = 3;
  66. [self.logoView addGestureRecognizer:doubleTap];
  67. self.logoView.userInteractionEnabled = YES;
  68. }
  69. - (void)didReceiveMemoryWarning {
  70. [super didReceiveMemoryWarning];
  71. // Dispose of any resources that can be recreated.
  72. }
  73. - (void)log:(NSString *)text {
  74. self.consoleView.text = [NSString stringWithFormat:@"%@%@ \n", self.consoleView.text, text];
  75. }
  76. - (IBAction)prepareForUnwind:(UIStoryboardSegue *)segue {
  77. //segue exit marker
  78. SettingsController *settingsController = segue.sourceViewController;
  79. self.reinstallBootstrapLabel.hidden = !settingsController.reinstallBootstrapSwitch.on;
  80. }
  81. - (IBAction)go:(UIButton *)sender {
  82. if (respringNeeded == YES) {
  83. [self restart];
  84. return;
  85. }
  86. self.goButton.enabled = NO;
  87. self.goButton.backgroundColor = UIColor.darkGrayColor;
  88. [self.goButton setTitle:@"jailbreaking" forState:UIControlStateDisabled];
  89. [self log:@"exploiting kernel"];
  90. kern_return_t ret = v0rtex(&tfp0, &kslide, &kcred);
  91. if (ret != KERN_SUCCESS) {
  92. self.goButton.enabled = YES;
  93. self.goButton.backgroundColor = GRAPE;
  94. [self.goButton setTitle:@"try again" forState:UIControlStateNormal];
  95. [self log:@"ERROR: exploit failed \n"];
  96. return;
  97. }
  98. LOG("v0rtex was successful");
  99. LOG("tfp0 -> %x", tfp0);
  100. LOG("slide -> 0x%llx", kslide);
  101. kbase = kslide + 0xFFFFFFF007004000;
  102. LOG("kern base -> 0x%llx", kbase);
  103. LOG("kern cred -> 0x%llx", kcred);
  104. [self bypassKPP];
  105. }
  106. - (void)bypassKPP {
  107. [self log:@"pwning kernel"];
  108. if (do_kpp(1, 0, kbase, kslide, tfp0) == KERN_SUCCESS) {
  109. LOG("you down with kpp? yeah you know me");
  110. [self remount];
  111. } else {
  112. [self log:@"ERROR: kpp bypass failed \n"];
  113. }
  114. }
  115. - (void)remount {
  116. [self log:@"remounting"];
  117. if (do_remount(kslide) == KERN_SUCCESS) {
  118. [self bootstrap];
  119. } else {
  120. [self log:@"ERROR: failed to remount system partition \n"];
  121. }
  122. }
  123. - (void)bootstrap {
  124. [self log:@"bootstrapping"];
  125. BOOL force = NO;
  126. if (self.reinstallBootstrapLabel.hidden == NO) {
  127. force = YES;
  128. [self log:@"(forcing reinstall)"];
  129. }
  130. if (do_bootstrap(force) == KERN_SUCCESS) {
  131. [self finish];
  132. } else {
  133. [self log:@"ERROR: failed to bootstrap \n"];
  134. }
  135. }
  136. - (void)finish {
  137. [self log:@"device is now jailbroken!"];
  138. [self log:@""];
  139. [self log:@"SSH server is ready on port 2222"];
  140. [self log:@"change your root/mobile passwords"];
  141. [self log:@""];
  142. [self log:@"respring to load tweaks"];
  143. sleep(2);
  144. LOG("reloading daemons...");
  145. pid_t pid;
  146. posix_spawn(&pid, "/bin/launchctl", 0, 0, (char**)&(const char*[]){"/bin/launchctl", "load", "/Library/LaunchDaemons/0.reload.plist", NULL}, NULL);
  147. waitpid(pid, 0, 0);
  148. sleep(2);
  149. respringNeeded = YES;
  150. [self.goButton setTitle:@"respring" forState:UIControlStateNormal];
  151. self.goButton.enabled = YES;
  152. }
  153. - (void)restart {
  154. LOG("restarting SpringBoard...");
  155. pid_t pid;
  156. const char* args[] = { "killall", "backboardd", NULL };
  157. posix_spawn(&pid, "/usr/bin/killall", NULL, NULL, (char* const*)args, NULL);
  158. }
  159. - (IBAction)fun:(UITapGestureRecognizer *)recognizer {
  160. LOG("got secret tap");
  161. if (!fun) {
  162. fun = YES;
  163. BOOL hasAudio = [AVAudioSession.sharedInstance setCategory:AVAudioSessionCategoryPlayback error:nil];
  164. if (!hasAudio) {
  165. LOG("no audio :/");
  166. }
  167. NSURL *url = [NSBundle.mainBundle URLForResource:@"y0nkers" withExtension:@"m4v"];
  168. LOG("url = %@", url);
  169. if (!url) {
  170. LOG("filenotfound");
  171. return;
  172. }
  173. player = [AVPlayer playerWithURL:url];
  174. cont = [[AVPlayerViewController alloc] init];
  175. cont.player = player;
  176. cont.showsPlaybackControls = NO;
  177. cont.updatesNowPlayingInfoCenter = NO;
  178. cont.view.frame = self.consoleView.bounds;
  179. [self.consoleView addSubview:cont.view];
  180. [player play];
  181. } else {
  182. [player pause];
  183. [cont.view removeFromSuperview];
  184. player = nil;
  185. cont = nil;
  186. fun = NO;
  187. }
  188. }
  189. @end