1717}
1818
1919NSString * installedPogoVersion (void ) {
20- NSLog (@" dmon: Finding Pogo version..." );
21- char bundlePath[150 ]; // This should never be longer than 100 but we added a buffer
20+ char path[1035 ];
2221 FILE *pogo_cmd = popen (" find /var/containers/Bundle/Application/ -type d -name 'PokmonGO.app'" , " r" );
22+ NSString *bundlePath = nil ;
2323 if (pogo_cmd == NULL ) {
2424 NSLog (@" dmon: Unable to find PokemonGo on device" );
2525 return nil ;
2626 }
2727
28- fgets (bundlePath, sizeof (bundlePath), pogo_cmd);
28+ // Read the output from the command
29+ if (fgets (path, sizeof (path)-1 , pogo_cmd) != NULL ) {
30+ bundlePath = [NSString stringWithUTF8String: path];
31+ bundlePath = [bundlePath stringByTrimmingCharactersInSet: [NSCharacterSet newlineCharacterSet ]];
32+ bundlePath = [bundlePath stringByAppendingPathComponent: @" Info.plist" ];
33+ }
34+
35+ // Close the file
2936 pclose (pogo_cmd);
30- bundlePath[strcspn (bundlePath, " \n " )] = ' \0 ' ; // Remove newline character
31- sprintf (bundlePath, " %s /Info.plist" , bundlePath);
32-
33- NSString *path = [[NSString alloc ] initWithUTF8String: bundlePath];
34- NSDictionary *infoDict = [[NSDictionary alloc ] initWithContentsOfFile: path];
35- NSString *versionString = [infoDict objectForKey: @" CFBundleShortVersionString" ];
36- NSLog (@" dmon: Installed version of Pokemon Go: %@ " , versionString);
37- return versionString;
37+
38+ NSFileHandle *fileHandle = [NSFileHandle fileHandleForReadingAtPath: bundlePath];
39+
40+ if (fileHandle) {
41+ // Read the contents of the file
42+ NSData *fileData = [fileHandle readDataToEndOfFile ];
43+ // Close the file handle
44+ [fileHandle closeFile ];
45+ // Convert the file data to a dictionary
46+ NSDictionary *infoDict = [NSPropertyListSerialization propertyListWithData: fileData options: NSPropertyListImmutable format: NULL error: NULL ];
47+ if (infoDict) {
48+ NSString *versionString = [infoDict objectForKey: @" CFBundleShortVersionString" ];
49+ NSLog (@" dmon: Version of Pokemon Go: %@ " , versionString);
50+ return versionString;
51+ }
52+ }
53+ else {
54+ NSLog (@" dmon: Failed to open file for reading: %@ " , bundlePath);
55+ }
56+
57+ return nil ;
3858}
3959
40- NSString * installedGCVersion (void ) {
41- // Can't use this really clean method since this library isn't versioned. Big Sad!
42- // NSBundle *goCheatsBundle = [NSBundle bundleWithPath:@"/Library/MobileSubstrate/DynamicLibraries/libgocheats.dylib"];
43- // NSLog(@"dmon: bundle info is: %@", goCheatsBundle);
44- // NSString *goCheatsVersion = [goCheatsBundle objectForInfoDictionaryKey:@"CFBundleShortVersionString"];
45- // NSLog(@"dmon: Version: %@", goCheatsVersion);
46- // return goCheatsVersion;
47-
48- NSLog (@" dmon: Finding GC version..." );
49- FILE *gc_cmd = popen (" apt list 2>/dev/null | grep -i gocheats | cut -d ' ' -f 2" , " r" );
50- if (gc_cmd == NULL ) {
51- NSLog (@" dmon: Unable to find GC version" );
60+ NSString *getAptList (NSString *packageName) {
61+ FILE *fp;
62+ char path[1035 ];
63+ NSString *command = [NSString stringWithFormat: @" dpkg-query --showformat='${Version}' --show %@ 2>/dev/null" , packageName];
64+ NSString *version = nil ;
65+
66+ // Open the command for reading
67+ fp = popen ([command UTF8String ], " r" );
68+ if (fp == NULL ) {
69+ NSLog (@" dmon: Failed to run command." );
5270 return nil ;
5371 }
5472
55- char version[256 ];
56- int bytesRead = fread (version, sizeof (char ), 255 , gc_cmd);
57- version[bytesRead] = ' \0 ' ;
58- pclose (gc_cmd);
59- version[strcspn (version, " \n " )] = ' \0 ' ; // Remove newline character
73+ // Read the output from the command
74+ if (fgets (path, sizeof (path)-1 , fp) != NULL ) {
75+ version = [NSString stringWithUTF8String: path];
76+ version = [version stringByTrimmingCharactersInSet: [NSCharacterSet newlineCharacterSet ]];
77+ }
78+
79+ // Close the file
80+ pclose (fp);
6081
61- NSLog (@" dmon: Installed version of GC : %s " , version);
62- return [[ NSString alloc ] initWithUTF8String: version] ;
82+ NSLog (@" dmon: Version of %@ : %@ " , packageName , version);
83+ return version;
6384}
6485
6586NSDictionary * parseConfig (void ) {
@@ -128,6 +149,7 @@ int installIpa(NSString *filePath) {
128149 FILE *install_ipa_cmd = popen (command, " r" );
129150 fscanf (install_ipa_cmd, " %d " , &results);
130151 pclose (install_ipa_cmd);
152+ NSLog (@" dmon: Results for %@ are: %d " , filePath, results);
131153 return results;
132154}
133155
@@ -148,8 +170,8 @@ int installDeb(NSString *filePath) {
148170
149171int downloadFile (NSString *url, NSString *userpass, NSString *outfile) {
150172 CURL *curl;
151- CURLcode res = -1 ;
152173 FILE *fp;
174+ long httpCode = -1 ;
153175 curl = curl_easy_init ();
154176
155177 if (curl) {
@@ -168,58 +190,75 @@ int downloadFile(NSString *url, NSString *userpass, NSString *outfile) {
168190 curl_easy_setopt (curl, CURLOPT_CAINFO, " /usr/lib/ssl/cacert.pem" );
169191
170192 // Perform the request
171- res = curl_easy_perform (curl);
172- NSLog (@" dmon: Curl return code for %@ : %u " , url, res);
193+ CURLcode res = curl_easy_perform (curl);
194+
195+ // Get the http status code
196+ curl_easy_getinfo (curl, CURLINFO_RESPONSE_CODE, &httpCode);
173197
174198 // Clean up
175199 fclose (fp);
176200 curl_easy_cleanup (curl);
201+
202+ // Check for successful download
203+ if (res == CURLE_OK && httpCode >= 200 && httpCode < 300 ) {
204+ NSLog (@" dmon: Download was sucessful: %ld " , httpCode);
205+ return 0 ;
206+ } else {
207+ NSLog (@" dmon: Download failed with error code: %ld " , httpCode);
208+ // Delete the outfile if it exists
209+ if (remove ([outfile UTF8String ]) != 0 ) {
210+ NSLog (@" Failed to delete the file %@ " , outfile);
211+ }
212+ }
177213 }
178- return res ;
214+ return - 1 ;
179215}
180216
181217void update (NSDictionary *config) {
182218 NSString *versionFile = @" version.txt" ;
183219 NSString *pogo_ipa = @" pogo.ipa" ;
184220 NSString *gc_deb = @" gc.deb" ;
185221 NSString *pogoVersion = installedPogoVersion ();
186- NSString *gcVersion = installedGCVersion ();
222+ NSString *gcVersion = getAptList (@" com.gocheats.jb" );
223+ // getAptList(@"com.github.clburlison.dmon");
187224
188225 // Strip trailing forward slashes to make things consistent for users
189226 NSString *url = [config[@" dmon_url" ] stringByTrimmingCharactersInSet: [NSCharacterSet characterSetWithCharactersInString: @" /" ]];
190227 NSLog (@" dmon: Update URL is: %@ " , url);
191- downloadFile (
228+ int versionDownload = downloadFile (
192229 [NSString stringWithFormat: @" %@ /%@ " , url, versionFile],
193230 [NSString stringWithFormat: @" %@ :%@ " , config[@" dmon_username" ], config[@" dmon_password" ]],
194231 versionFile
195232 );
233+ if (versionDownload != 0 ) {
234+ NSLog (@" dmon: Unable to process updates as %@ is invalid" , versionFile);
235+ return ;
236+ }
196237
197238 // Parse the config map style version.txt to NSDictionary
198239 NSMutableDictionary *parsedVersion = parseKeyValueFileAtPath (versionFile);
199240
200241 // Update Pogo if needed
201242 if (![pogoVersion isEqualToString: parsedVersion[@" pogo" ]]) {
202- NSLog (@" dmon: Pogo version mismatch. Have %@ . Need %@ " , pogoVersion, parsedVersion[@" pogo" ]);
243+ NSLog (@" dmon: Pogo version mismatch. Have ' %@ ' . Need ' %@ ' " , pogoVersion, parsedVersion[@" pogo" ]);
203244 int pogoDownload = downloadFile (
204245 [NSString stringWithFormat: @" %@ /%@ " , url, pogo_ipa],
205246 [NSString stringWithFormat: @" %@ :%@ " , config[@" dmon_username" ], config[@" dmon_password" ]],
206247 pogo_ipa
207248 );
208- // TODO: Do we need a stricter validation?
209249 if (pogoDownload == 0 ) {
210250 installIpa (pogo_ipa);
211251 }
212252 }
213253
214254 // Update GC if needed
215255 if (![gcVersion isEqualToString: parsedVersion[@" gc" ]]) {
216- NSLog (@" dmon: GC version mismatch. Have %@ . Need %@ " , gcVersion, parsedVersion[@" gc" ]);
256+ NSLog (@" dmon: GC version mismatch. Have ' %@ ' . Need ' %@ ' " , gcVersion, parsedVersion[@" gc" ]);
217257 int gcDownload = downloadFile (
218258 [NSString stringWithFormat: @" %@ /%@ " , url, gc_deb],
219259 [NSString stringWithFormat: @" %@ :%@ " , config[@" dmon_username" ], config[@" dmon_password" ]],
220260 gc_deb
221261 );
222- // TODO: Do we need a stricter validation?
223262 if (gcDownload == 0 ) {
224263 installDeb (gc_deb);
225264 }
@@ -233,9 +272,17 @@ void monitor(void) {
233272 killall (@" /usr/bin/kernbypass" );
234273 NSLog (@" dmon: Force stopping Pogo..." );
235274 killall (@" pokemongo" );
236- sleep (2 );
237- NSLog (@" dmon: Pogo not running. Launch it..." );
275+ sleep (5 );
276+
277+ // Attempt to check versions and update now that Pogo & Kernbypass are not running
278+ NSDictionary *config = parseConfig ();
279+ if (config[@" dmon_url" ] != nil && [config[@" dmon_url" ] isKindOfClass: [NSString class ]] && ![config[@" dmon_url" ] isEqualToString: @" " ]) {
280+ // NSLog(@"dmon: Full config: %@", config);
281+ update (config);
282+ }
283+
238284 // Launch Pogo
285+ NSLog (@" dmon: Pogo not running. Launch it..." );
239286 void * sbServices = dlopen (" /System/Library/PrivateFrameworks/SpringBoardServices.framework/SpringBoardServices" , RTLD_LAZY);
240287 int (*SBSLaunchApplicationWithIdentifier)(CFStringRef identifier, Boolean suspended) = dlsym (sbServices, " SBSLaunchApplicationWithIdentifier" );
241288 NSString *bundleString=[NSString stringWithUTF8String: " com.nianticlabs.pokemongo" ];
@@ -249,23 +296,8 @@ int main(void) {
249296 NSLog (@" dmon: Starting..." );
250297
251298 // Start loop
252- int i = 0 ;
253299 while (1 ) {
254- // Only call at the start of loop
255- if (i == 0 ) {
256- NSDictionary *config = parseConfig ();
257- // NSLog(@"dmon: Full config: %@", config);
258- update (config);
259- }
260-
261- // Call this function every loop
262300 monitor ();
263-
264- // Restart loop on the 30th iteration
265- if (++i == 30 ) {
266- i = 0 ;
267- }
268-
269301 sleep (30 );
270302 }
271303 return 0 ;
0 commit comments