HelperClass.m 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402
  1. #import "HelperClass.h"
  2. #import "StatusPackageModel.h"
  3. @implementation HelperClass
  4. + (NSArray <StatusPackageModel*>*)statusInstalledPackagesFromFile:(NSString *)statusFile
  5. {
  6. if (![FM fileExistsAtPath:statusFile]) {
  7. return nil;
  8. }
  9. NSString *packageString = [NSString stringWithContentsOfFile:statusFile encoding:NSUTF8StringEncoding error:nil];
  10. NSArray *lineArray = [packageString componentsSeparatedByString:@"\n\n"];
  11. //DLog(@"lineArray: %@", lineArray);
  12. NSMutableArray *mutableList = [[NSMutableArray alloc] init];
  13. //NSMutableDictionary *mutableDict = [[NSMutableDictionary alloc] init];
  14. for (id currentItem in lineArray)
  15. {
  16. StatusPackageModel *debModel = [[StatusPackageModel alloc] initWithRawControlString:currentItem];
  17. if (debModel != nil)
  18. [mutableList addObject:debModel];
  19. }
  20. NSSortDescriptor *nameDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:YES
  21. selector:@selector(localizedCaseInsensitiveCompare:)];
  22. NSSortDescriptor *packageDescriptor = [[NSSortDescriptor alloc] initWithKey:@"package" ascending:YES
  23. selector:@selector(localizedCaseInsensitiveCompare:)];
  24. NSArray *descriptors = [NSArray arrayWithObjects:nameDescriptor, packageDescriptor, nil];
  25. NSArray *sortedArray = [mutableList sortedArrayUsingDescriptors:descriptors];
  26. mutableList = nil;
  27. return sortedArray;
  28. }
  29. + (BOOL)shouldContinueWithError:(NSString *)errorMessage {
  30. NSString *errorString = [NSString stringWithFormat:@"\n%@ Are you sure you want to continue? [y/n]?", errorMessage];
  31. char c;
  32. printf("%s", [errorString UTF8String] );
  33. c=getchar();
  34. while(c!='y' && c!='n')
  35. {
  36. if (c!='\n'){
  37. printf("[y/n]");
  38. }
  39. c=getchar();
  40. }
  41. if (c == 'n')
  42. {
  43. DLog(@"\nSmart move... exiting\n\n");
  44. return FALSE;
  45. } else if (c == 'y') {
  46. DLog(@"\nDon't say we didn't warn ya!....\n");
  47. }
  48. return TRUE;
  49. }
  50. + (NSArray *)arrayReturnForTask:(NSString *)taskBinary withArguments:(NSArray *)taskArguments
  51. {
  52. NSLog(@"%@ %@", taskBinary, [taskArguments componentsJoinedByString:@" "]);
  53. NSTask *task = [[NSTask alloc] init];
  54. NSPipe *pipe = [[NSPipe alloc] init];
  55. NSFileHandle *handle = [pipe fileHandleForReading];
  56. [task setLaunchPath:taskBinary];
  57. [task setArguments:taskArguments];
  58. [task setStandardOutput:pipe];
  59. [task setStandardError:pipe];
  60. [task launch];
  61. NSData *outData = nil;
  62. NSString *temp = nil;
  63. while((outData = [handle readDataToEndOfFile]) && [outData length])
  64. {
  65. temp = [[NSString alloc] initWithData:outData encoding:NSASCIIStringEncoding];
  66. }
  67. [handle closeFile];
  68. task = nil;
  69. return [temp componentsSeparatedByString:@"\n"];
  70. }
  71. + (NSString *)singleLineReturnForProcess:(NSString *)call
  72. {
  73. return [[self returnForProcess:call] componentsJoinedByString:@"\n"];
  74. }
  75. + (NSArray *)returnForProcess:(NSString *)call
  76. {
  77. if (call==nil)
  78. return 0;
  79. char line[200];
  80. DLog(@"\nRunning process: %@\n", call);
  81. FILE* fp = popen([call UTF8String], "r");
  82. NSMutableArray *lines = [[NSMutableArray alloc]init];
  83. if (fp)
  84. {
  85. while (fgets(line, sizeof line, fp))
  86. {
  87. NSString *s = [NSString stringWithCString:line encoding:NSUTF8StringEncoding];
  88. s = [s stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
  89. [lines addObject:s];
  90. }
  91. }
  92. pclose(fp);
  93. return lines;
  94. }
  95. + (InputPackageFile *)packageFileFromLine:(NSString *)inputLine {
  96. // "-rwxr-xr-x 0 root wheel 69424 Oct 22 03:56 ./Library/MobileSubstrate/DynamicLibraries/beigelist7.dylib\n",
  97. //-rwxr-xr-x root/staff 10860 2011-02-02 03:55 ./Library/Frameworks/CydiaSubstrate.framework/Commands/cycc
  98. inputLine = [inputLine stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
  99. inputLine = [inputLine stringByTrimmingCharactersInSet:[NSCharacterSet characterSetWithCharactersInString:@"\t"]];
  100. NSMutableString *newString = [[NSMutableString alloc] initWithString:inputLine];
  101. [newString replaceOccurrencesOfString:@" " withString:@" " options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
  102. [newString replaceOccurrencesOfString:@" " withString:@" " options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
  103. [newString replaceOccurrencesOfString:@" " withString:@" " options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
  104. [newString replaceOccurrencesOfString:@" " withString:@" " options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
  105. [newString replaceOccurrencesOfString:@" " withString:@" " options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
  106. NSArray *lineObjects = [newString componentsSeparatedByString:@" "];
  107. //NSLog(@"lineObjects: %@", lineObjects);
  108. /*
  109. "drwxr-xr-x",
  110. "root/wheel",
  111. 0,
  112. "2018-06-27",
  113. "01:21",
  114. "./"
  115. */
  116. NSString *permissionsAndType = [lineObjects objectAtIndex:0];
  117. NSString *userGroup = [lineObjects objectAtIndex:1];
  118. NSString *size = [lineObjects objectAtIndex:2];
  119. NSString *date = [lineObjects objectAtIndex:3];
  120. NSString *time = [lineObjects objectAtIndex:4];
  121. NSString *path = [lineObjects objectAtIndex:5];
  122. //@"drwxr-xr-x"
  123. NSString *fileTypeChar = [permissionsAndType substringWithRange:NSMakeRange(0, 1)];
  124. NSString *octalPermissions = [self octalFromSymbols:permissionsAndType];
  125. NSString *octalUG = [self octalFromGroupSymbols:userGroup];
  126. NSString *fileName = [path lastPathComponent];
  127. //NSString *fullPath = [NSString stringWithFormat:@"/%@", path];
  128. NSString *fullPath = [path substringFromIndex:1];
  129. InputPackageFile *pf = [InputPackageFile new];
  130. [pf _setFileTypeFromRaw:fileTypeChar];
  131. switch (pf.type) {
  132. case BSPackageFileTypeLink:
  133. {
  134. fullPath = [lineObjects objectAtIndex:7];
  135. NSString *linkDest = [NSString stringWithFormat:@"/%@", path];
  136. pf.permissions = octalPermissions;
  137. pf.owner = octalUG;
  138. pf.size = size;
  139. pf.time = time;
  140. pf.date = date;
  141. pf.path = fullPath;
  142. pf.basename = fileName;
  143. pf.linkDestination = linkDest;
  144. return pf;
  145. }
  146. break;
  147. case BSPackageFileTypeDirectory: //return for now
  148. //DLog(@"we dont want directory entries do we %@", lineObjects);
  149. pf.permissions = octalPermissions;
  150. pf.owner = octalUG;
  151. pf.size = size;
  152. pf.time = time;
  153. pf.date = date;
  154. pf.path = fullPath;
  155. pf.basename = fileName;
  156. return pf;
  157. break;
  158. default:
  159. break;
  160. }
  161. pf.permissions = octalPermissions;
  162. pf.owner = octalUG;
  163. pf.size = size;
  164. pf.time = time;
  165. pf.date = date;
  166. pf.path = fullPath;
  167. pf.basename = fileName;
  168. return pf;
  169. // return [NSDictionary dictionaryWithObjectsAndKeys:fileType, @"fileType",octalPermissions, @"octalPermissions", octalUG, @"octalUG", size, @"size", date, @"date", time, @"time", fileName, @"fileName", fullPath, @"fullPath", nil];
  170. }
  171. + (NSString *)octalFromGroupSymbols:(NSString *)theSymbols
  172. {
  173. NSArray *groupArray = [theSymbols componentsSeparatedByString:@"/"];
  174. NSString *user = [groupArray objectAtIndex:0];
  175. NSString *group = [groupArray objectAtIndex:1];
  176. NSString *octalUser = nil;
  177. NSString *octalGroup = nil;
  178. //uid=0(root) gid=0(wheel) groups=0(wheel),1(daemon),2(kmem),3(sys),4(tty),5(operator),8(procview),9(procmod),20(staff),29(certusers),80(admin)
  179. if ([user isEqualToString:@"root"])
  180. {
  181. octalUser = @"0";
  182. } else if ([user isEqualToString:@"mobile"])
  183. {
  184. octalUser = @"501";
  185. }
  186. //obviously more cases!! FIXME:
  187. if ([group isEqualToString:@"staff"])
  188. {
  189. octalGroup = @"20";
  190. } else if ([group isEqualToString:@"admin"])
  191. {
  192. octalGroup = @"80";
  193. } else if ([group isEqualToString:@"wheel"])
  194. {
  195. octalGroup = @"0";
  196. } else if ([group isEqualToString:@"daemon"])
  197. {
  198. octalGroup = @"1";
  199. } else if ([group isEqualToString:@"kmem"])
  200. {
  201. octalGroup = @"2";
  202. } else if ([group isEqualToString:@"sys"])
  203. {
  204. octalGroup = @"3";
  205. } else if ([group isEqualToString:@"tty"])
  206. {
  207. octalGroup = @"4";
  208. } else if ([group isEqualToString:@"operator"])
  209. {
  210. octalGroup = @"5";
  211. } else if ([group isEqualToString:@"procview"])
  212. {
  213. octalGroup = @"8";
  214. } else if ([group isEqualToString:@"procmod"])
  215. {
  216. octalGroup = @"9";
  217. } else if ([group isEqualToString:@"certusers"])
  218. {
  219. octalGroup = @"29";
  220. } else
  221. {
  222. octalGroup = @"501"; //default to mobile
  223. }
  224. //uid=0(root) gid=0(wheel) groups=0(wheel),1(daemon),2(kmem),3(sys),4(tty),5(operator),8(procview),9(procmod),20(staff),29(certusers),80(admin)
  225. return [NSString stringWithFormat:@"%@:%@", octalUser, octalGroup];
  226. }
  227. + (InputPackage *)packageForDeb:(NSString *)debFile {
  228. NSString *packageName = [self singleLineReturnForProcess:[NSString stringWithFormat:@"/usr/local/bin/dpkg -f %@ Package", debFile]];
  229. NSString *packageVersion = [self singleLineReturnForProcess:[NSString stringWithFormat:@"/usr/local/bin/dpkg -f %@ Version", debFile]];
  230. NSArray <InputPackageFile *> *fileList = [self returnForProcess:[NSString stringWithFormat:@"/usr/local/bin/dpkg -c %@", debFile]];
  231. __block NSMutableArray *finalArray = [NSMutableArray new];
  232. [fileList enumerateObjectsUsingBlock:^(id _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
  233. InputPackageFile *file = [self packageFileFromLine:obj];
  234. if (file) {
  235. //DLog(@"%@", file);
  236. [finalArray addObject:file];
  237. }
  238. }];
  239. InputPackage *pkg = [InputPackage new];
  240. pkg.files = finalArray;
  241. pkg.path = debFile;
  242. pkg.packageName = packageName;
  243. pkg.version = packageVersion;
  244. return pkg;
  245. }
  246. + (NSString *)octalFromSymbols:(NSString *)theSymbols
  247. {
  248. //NSLog(@"%@ %s", self, _cmd);
  249. NSString *U = [theSymbols substringWithRange:NSMakeRange(1, 3)];
  250. NSString *G = [theSymbols substringWithRange:NSMakeRange(4, 3)];
  251. NSString *O = [theSymbols substringWithRange:NSMakeRange(7, 3)];
  252. //NSLog(@"fileTypeChar: %@", fileTypeChar);
  253. //NSLog(@"U; %@", U);
  254. //NSLog(@"G; %@", G);
  255. //NSLog(@"O; %@", O);
  256. //USER
  257. int sIdBit = 0;
  258. int uOctal = 0;
  259. const char *uArray = [U cStringUsingEncoding:NSASCIIStringEncoding];
  260. int stringLength = [U length];
  261. int x;
  262. for( x=0; x<stringLength; x++ )
  263. {
  264. unsigned int aCharacter = uArray[x];
  265. if (aCharacter == 'r')
  266. {
  267. uOctal += 4;
  268. } else if (aCharacter == 'w')
  269. {
  270. uOctal += 2;
  271. } else if (aCharacter == 'x')
  272. {
  273. uOctal += 1;
  274. } else if (aCharacter == 's')
  275. {
  276. sIdBit += 4;
  277. }
  278. }
  279. //GROUP
  280. int gOctal = 0;
  281. const char *gArray = [G cStringUsingEncoding:NSASCIIStringEncoding];
  282. stringLength = [G length];
  283. int y;
  284. for( y=0; y<stringLength; y++ )
  285. {
  286. unsigned int aCharacter = gArray[y];
  287. if (aCharacter == 'r')
  288. {
  289. gOctal += 4;
  290. } else if (aCharacter == 'w')
  291. {
  292. gOctal += 2;
  293. } else if (aCharacter == 'x')
  294. {
  295. gOctal += 1;
  296. } else if (aCharacter == 's')
  297. {
  298. gOctal += 2;
  299. }
  300. }
  301. //OTHERS
  302. int z;
  303. int oOctal = 0;
  304. const char *oArray = [O cStringUsingEncoding:NSASCIIStringEncoding];
  305. stringLength = [O length];
  306. for( z=0; z<stringLength; z++ )
  307. {
  308. unsigned int aCharacter = oArray[z];
  309. if (aCharacter == 'r')
  310. {
  311. oOctal += 4;
  312. } else if (aCharacter == 'w')
  313. {
  314. oOctal += 2;
  315. } else if (aCharacter == 'x')
  316. {
  317. oOctal += 1;
  318. }
  319. }
  320. return [NSString stringWithFormat:@"%i%i%i%i", sIdBit, uOctal, gOctal, oOctal];
  321. }
  322. @end