/* Cydia - iPhone UIKit Front-End for Debian APT
- * Copyright (C) 2008 Jay Freeman (saurik)
+ * Copyright (C) 2008-2009 Jay Freeman (saurik)
*/
/*
#define USE_SYSTEM_MALLOC 1
/* #include Directives {{{ */
-#import "UICaboodle.h"
+#import "UICaboodle/UCPlatform.h"
+#import "UICaboodle/UCLocalize.h"
#include <objc/message.h>
#include <objc/objc.h>
#include <CoreFoundation/CFPriv.h>
#include <CoreFoundation/CFUniChar.h>
-#import <QuartzCore/CALayer.h>
#import <UIKit/UIKit.h>
#include <WebCore/WebCoreThread.h>
#include <ext/hash_map>
-#import "BrowserView.h"
-#import "ResetView.h"
+#import "UICaboodle/BrowserView.h"
+#import "UICaboodle/ResetView.h"
#import "substrate.h"
/* }}} */
}
public:
+ _finline _H(const This_ &rhs) :
+ value_(rhs.value_ == nil ? nil : [rhs.value_ retain])
+ {
+ }
+
_finline _H(Type_ *value = NULL, bool mended = false) :
value_(value)
{
#endif
/* }}} */
-extern NSString * const kCAFilterNearest;
-
/* Information Dictionaries {{{ */
@interface NSMutableArray (Cydia)
- (void) addInfoDictionary:(NSDictionary *)info;
#define lprintf(args...) fprintf(stderr, args)
-#define ForRelease 0
+#define ForRelease 1
#define TraceLogging (1 && !ForRelease)
#define HistogramInsertionSort (0 && !ForRelease)
#define ProfileTimes (0 && !ForRelease)
@end
-static inline NSString *CYLocalizeEx(NSString *key, NSString *value = nil) {
- return [[NSBundle mainBundle] localizedStringForKey:key value:value table:nil];
-}
-
-#define CYLocalize(key) CYLocalizeEx(@ key)
-
class CYString {
private:
char *data_;
CFStringRef cache_;
_finline void clear_() {
- if (cache_ != nil)
+ if (cache_ != NULL) {
CFRelease(cache_);
+ cache_ = NULL;
+ }
}
public:
_finline CYString() :
data_(0),
size_(0),
- cache_(nil)
+ cache_(NULL)
{
}
static const float KeyboardTime_ = 0.3f;
#define SpringBoard_ "/System/Library/LaunchDaemons/com.apple.SpringBoard.plist"
-#define SandboxTemplate_ "/usr/share/sandbox/SandboxTemplate.sb"
#define NotifyConfig_ "/etc/notify.conf"
static bool Queuing_;
NSDate *update = [Metadata_ objectForKey:@"LastUpdate"];
if (update == nil)
- return CYLocalize("NEVER_OR_UNKNOWN");
+ return UCLocalize("NEVER_OR_UNKNOWN");
CFDateFormatterRef formatter = CFDateFormatterCreate(NULL, Locale_, kCFDateFormatterMediumStyle, kCFDateFormatterMediumStyle);
CFStringRef formatted = CFDateFormatterCreateStringWithDate(NULL, formatter, (CFDateRef) update);
return CFStringCreateWithBytesNoCopy(kCFAllocatorDefault, reinterpret_cast<const uint8_t *>(value), strlen(value), kCFStringEncodingUTF8, NO, kCFAllocatorNull);
}
+const char *StripVersion_(const char *version) {
+ const char *colon(strchr(version, ':'));
+ if (colon != NULL)
+ version = colon + 1;
+ return version;
+}
+
CFStringRef StripVersion(const char *version) {
const char *colon(strchr(version, ':'));
if (colon != NULL)
version = colon + 1;
+ return CFStringCreateWithBytes(kCFAllocatorDefault, reinterpret_cast<const uint8_t *>(version), strlen(version), kCFStringEncodingUTF8, NO);
+ // XXX: performance
return CFCString(version);
}
NSString *parent(title_r[1]);
NSString *child(title_r[2]);
- return [NSString stringWithFormat:CYLocalize("PARENTHETICAL"),
+ return [NSString stringWithFormat:UCLocalize("PARENTHETICAL"),
LocalizeSection(parent),
LocalizeSection(child)
];
- (void) askForSettings;
- (UIProgressHUD *) addProgressHUD;
- (void) removeProgressHUD:(UIProgressHUD *)hud;
-- (RVPage *) pageForURL:(NSURL *)url hasTag:(int *)tag;
- (RVPage *) pageForPackage:(NSString *)name;
-- (void) openMailToURL:(NSURL *)url;
-- (void) clearFirstResponder;
- (PackageView *) packageView;
@end
/* }}} */
- (void) upgrade;
- (void) update;
-- (void) updateWithStatus:(Status &)status;
+- (NSString *) updateWithStatus:(Status &)status;
- (void) setDelegate:(id)delegate;
- (Source *) getSource:(pkgCache::PkgFileIterator)file;
/* Source Class {{{ */
@interface Source : NSObject {
+ CYString depiction_;
CYString description_;
CYString label_;
CYString origin_;
- (NSComparisonResult) compareByNameAndType:(Source *)source;
+- (NSString *) depictionForPackage:(NSString *)package;
- (NSString *) supportForPackage:(NSString *)package;
- (NSDictionary *) record;
description_.clear();
label_.clear();
origin_.clear();
+ depiction_.clear();
support_.clear();
version_.clear();
defaultIcon_.clear();
debReleaseIndex *dindex(dynamic_cast<debReleaseIndex *>(index));
if (dindex != NULL) {
- FileFd fd(dindex->MetaIndexFile("Release"), FileFd::ReadOnly);
- pkgTagFile tags(&fd);
+ FileFd fd;
+ if (!fd.Open(dindex->MetaIndexFile("Release"), FileFd::ReadOnly))
+ _error->Discard();
+ else {
+ pkgTagFile tags(&fd);
- pkgTagSection section;
- tags.Step(section);
+ pkgTagSection section;
+ tags.Step(section);
- struct {
- const char *name_;
- CYString *value_;
- } names[] = {
- {"default-icon", &defaultIcon_},
- {"description", &description_},
- {"label", &label_},
- {"origin", &origin_},
- {"support", &support_},
- {"version", &version_},
- };
-
- for (size_t i(0); i != sizeof(names) / sizeof(names[0]); ++i) {
- const char *start, *end;
+ struct {
+ const char *name_;
+ CYString *value_;
+ } names[] = {
+ {"default-icon", &defaultIcon_},
+ {"depiction", &depiction_},
+ {"description", &description_},
+ {"label", &label_},
+ {"origin", &origin_},
+ {"support", &support_},
+ {"version", &version_},
+ };
+
+ for (size_t i(0); i != sizeof(names) / sizeof(names[0]); ++i) {
+ const char *start, *end;
- if (section.Find(names[i].name_, start, end)) {
- CYString &value(*names[i].value_);
- value.set(pool, start, end - start);
+ if (section.Find(names[i].name_, start, end)) {
+ CYString &value(*names[i].value_);
+ value.set(pool, start, end - start);
+ }
}
}
}
return [lhs compare:rhs options:LaxCompareOptions_];
}
+- (NSString *) depictionForPackage:(NSString *)package {
+ return depiction_.empty() ? nil : [depiction_ stringByReplacingOccurrencesOfString:@"*" withString:package];
+}
+
- (NSString *) supportForPackage:(NSString *)package {
return support_.empty() ? nil : [support_ stringByReplacingOccurrencesOfString:@"*" withString:package];
}
bool visible_;
NSString *latest_;
- NSString *installed_;
+ CYString installed_;
CYString id_;
CYString name_;
- (NSString *) latest;
- (NSString *) installed;
+- (BOOL) uninstalled;
- (BOOL) valid;
- (BOOL) upgradableAndEssential:(BOOL)essential;
if (latest_ != nil)
[latest_ release];
- if (installed_ != nil)
- [installed_ release];
if (sponsor$_ != nil)
[sponsor$_ release];
_profile(Package$initWithVersion$Versions)
current = iterator_.CurrentVer();
if (!current.end())
- installed_ = (NSString *) StripVersion(current.VerStr());
+ installed_.set(pool_, StripVersion_(current.VerStr()));
if (!version_.end())
file_ = version_.FileList();
_end
}
+ visible_ = true;
+
_profile(Package$initWithVersion$Tags)
pkgCache::TagIterator tag(iterator_.TagList());
if (!tag.end()) {
do {
const char *name(tag.Name());
[tags_ addObject:(NSString *)CFCString(name)];
- if (role_ == nil && strncmp(name, "role::", 6) == 0)
+ if (role_ == nil && strncmp(name, "role::", 6) == 0 /*&& strcmp(name, "role::leaper") != 0*/)
role_ = (NSString *) CFCString(name + 6);
+ if (visible_ && strncmp(name, "require::", 9) == 0 && (
+ true
+ ))
+ visible_ = false;
++tag;
} while (!tag.end());
}
if (version == nil) {
[metadata_ setObject:latest_ forKey:@"LastVersion"];
changed = true;
- } else if (![version isEqualToString:latest_]) {
+ } else {
+ if (![version isEqualToString:latest_]) {
[metadata_ setObject:latest_ forKey:@"LastVersion"];
lastSeen_ = now_;
[metadata_ setObject:lastSeen_ forKey:@"LastSeen"];
changed = true;
- }
+ } }
}
metadata_ = [metadata_ retain];
_end
essential_ = ((iterator_->Flags & pkgCache::Flag::Essential) == 0 ? NO : YES) || [self hasTag:@"cydia::essential"];
- visible_ = [self hasSupportingRole] && [self unfiltered];
+ visible_ = visible_ && [self hasSupportingRole] && [self unfiltered];
} _end } return self;
}
+ (Package *) packageWithIterator:(pkgCache::PkgIterator)iterator withZone:(NSZone *)zone inPool:(apr_pool_t *)pool database:(Database *)database {
+@synchronized ([Database class]) {
pkgCache::VerIterator version;
_profile(Package$packageWithIterator$GetCandidateVer)
inPool:pool
database:database
] autorelease];
-}
+} }
- (pkgCache::PkgIterator) iterator {
return iterator_;
}
- (NSString *) longSection {
- return LocalizeSection(section_);
+ return LocalizeSection([self section]);
}
- (NSString *) shortSection {
return installed_;
}
+- (BOOL) uninstalled {
+ return installed_.empty();
+}
+
- (BOOL) valid {
return !version_.end();
}
}
- (NSString *) depiction {
- return depiction_;
+ return !depiction_.empty() ? depiction_ : [[self source] depictionForPackage:id_];
}
- (Address *) sponsor {
size_t length(strlen(name));
if (length < 2) invalid:
- [warnings addObject:CYLocalize("ILLEGAL_PACKAGE_IDENTIFIER")];
+ [warnings addObject:UCLocalize("ILLEGAL_PACKAGE_IDENTIFIER")];
else for (size_t i(0); i != length; ++i)
if (
/* XXX: technically this is not allowed */
/* XXX: this is not sensitive enough. only some folders are valid. */
if (cydia && !repository)
- [warnings addObject:[NSString stringWithFormat:CYLocalize("FILES_INSTALLED_TO"), @"Cydia.app"]];
+ [warnings addObject:[NSString stringWithFormat:UCLocalize("FILES_INSTALLED_TO"), @"Cydia.app"]];
if (_private)
- [warnings addObject:[NSString stringWithFormat:CYLocalize("FILES_INSTALLED_TO"), @"/private"]];
+ [warnings addObject:[NSString stringWithFormat:UCLocalize("FILES_INSTALLED_TO"), @"/private"]];
if (stash)
- [warnings addObject:[NSString stringWithFormat:CYLocalize("FILES_INSTALLED_TO"), @"/var/stash"]];
+ [warnings addObject:[NSString stringWithFormat:UCLocalize("FILES_INSTALLED_TO"), @"/var/stash"]];
}
return [warnings count] == 0 ? nil : warnings;
}
- (bool) isInstalledAndVisible:(NSNumber *)number {
- return (![number boolValue] || [self visible]) && [self installed] != nil;
+ return (![number boolValue] || [self visible]) && ![self uninstalled];
}
- (bool) isVisiblyUninstalledInSection:(NSString *)name {
return
[self visible] &&
- [self installed] == nil && (
+ [self uninstalled] && (
name == nil ||
section == nil && [name length] == 0 ||
[name isEqualToString:section]
}
- (Package *) packageWithName:(NSString *)name {
+@synchronized ([Database class]) {
if (static_cast<pkgDepCache *>(cache_) == NULL)
return nil;
pkgCache::PkgIterator iterator(cache_->FindPkg([name UTF8String]));
return iterator.end() ? nil : [Package packageWithIterator:iterator withZone:NULL inPool:pool_ database:self];
-}
+} }
- (Database *) init {
if ((self = [super init]) != nil) {
}
- (void) reloadData { _pooled
+@synchronized ([Database class]) {
+
@synchronized (self) {
++era_;
}
_trace();
}
-}
+} }
- (void) configure {
NSString *dpkg = [NSString stringWithFormat:@"dpkg --configure -a --status-fd %u", statusfd_];
for (pkgAcquire::ItemIterator item = fetcher_->ItemsBegin(); item != fetcher_->ItemsEnd(); item++) {
if ((*item)->Status == pkgAcquire::Item::StatDone && (*item)->Complete)
continue;
+ if ((*item)->Status == pkgAcquire::Item::StatIdle)
+ continue;
std::string uri = (*item)->DescURI();
std::string error = (*item)->ErrorText;
[self updateWithStatus:status_];
}
-- (void) updateWithStatus:(Status &)status {
+- (NSString *) updateWithStatus:(Status &)status {
pkgSourceList list;
_assert(list.ReadMainList());
FileFd lock;
lock.Fd(GetLock(_config->FindDir("Dir::State::Lists") + "lock"));
- _assert(!_error->PendingError());
+
+ if (_error->PendingError()) {
+ std::string error;
+ if (!_error->PopMessage(error))
+ _assert(false);
+ _error->Discard();
+ return [NSString stringWithUTF8String:error.c_str()];
+ }
pkgAcquire fetcher(&status);
_assert(list.GetIndexes(&fetcher));
[Metadata_ setObject:[NSDate date] forKey:@"LastUpdate"];
Changed_ = true;
}
+
+ return nil;
}
- (void) setDelegate:(id)delegate {
}
- (Source *) getSource:(pkgCache::PkgFileIterator)file {
- return sources_[file->ID];
+ SourceMap::const_iterator i(sources_.find(file->ID));
+ return i == sources_.end() ? nil : i->second;
}
@end
@end
/* }}} */
-#if 0
-/* Mail Composition {{{ */
-@interface MailToView : PopUpView {
- MailComposeController *controller_;
+/* Confirmation View {{{ */
+bool DepSubstrate(const pkgCache::VerIterator &iterator) {
+ if (!iterator.end())
+ for (pkgCache::DepIterator dep(iterator.DependsList()); !dep.end(); ++dep) {
+ if (dep->Type != pkgCache::Dep::Depends && dep->Type != pkgCache::Dep::PreDepends)
+ continue;
+ pkgCache::PkgIterator package(dep.TargetPkg());
+ if (package.end())
+ continue;
+ if (strcmp(package.Name(), "mobilesubstrate") == 0)
+ return true;
+ }
+
+ return false;
}
-- (id) initWithView:(UIView *)view delegate:(id)delegate url:(NSURL *)url;
+/* Web Scripting {{{ */
+@interface CydiaObject : NSObject {
+ id indirect_;
+}
+- (id) initWithDelegate:(IndirectDelegate *)indirect;
@end
-@implementation MailToView
+@implementation CydiaObject
- (void) dealloc {
- [controller_ release];
+ [indirect_ release];
[super dealloc];
}
-- (void) mailComposeControllerWillAttemptToSend:(MailComposeController *)controller {
- NSLog(@"will");
+- (id) initWithDelegate:(IndirectDelegate *)indirect {
+ if ((self = [super init]) != nil) {
+ indirect_ = [indirect retain];
+ } return self;
+}
+
++ (NSArray *) _attributeKeys {
+ return [NSArray arrayWithObjects:@"device", @"firewire", @"imei", @"mac", @"serial", nil];
+}
+
+- (NSArray *) attributeKeys {
+ return [[self class] _attributeKeys];
+}
+
++ (BOOL) isKeyExcludedFromWebScript:(const char *)name {
+ return ![[self _attributeKeys] containsObject:[NSString stringWithUTF8String:name]] && [super isKeyExcludedFromWebScript:name];
}
-- (void) mailComposeControllerDidAttemptToSend:(MailComposeController *)controller mailDelivery:(id)delivery {
- NSLog(@"did:%@", delivery);
-// [UIApp setStatusBarShowsProgress:NO];
-if ([controller error]){
-NSArray *buttons = [NSArray arrayWithObjects:CYLocalize("OK"), nil];
-UIActionSheet *mailAlertSheet = [[UIActionSheet alloc] initWithTitle:CYLocalize("ERROR") buttons:buttons defaultButtonIndex:0 delegate:self context:self];
-[mailAlertSheet setBodyText:[controller error]];
-[mailAlertSheet popupAlertAnimated:YES];
+- (NSString *) device {
+ return [[UIDevice currentDevice] uniqueIdentifier];
}
+
+#if 0 // XXX: implement!
+- (NSString *) mac {
+ if (![indirect_ promptForSensitive:@"Mac Address"])
+ return nil;
}
-- (void) showError {
- NSLog(@"%@", [controller_ error]);
- NSArray *buttons = [NSArray arrayWithObjects:CYLocalize("OK"), nil];
- UIActionSheet *mailAlertSheet = [[UIActionSheet alloc] initWithTitle:CYLocalize("ERROR") buttons:buttons defaultButtonIndex:0 delegate:self context:self];
- [mailAlertSheet setBodyText:[controller_ error]];
- [mailAlertSheet popupAlertAnimated:YES];
+- (NSString *) serial {
+ if (![indirect_ promptForSensitive:@"Serial #"])
+ return nil;
}
-- (void) deliverMessage { _pooled
- setuid(501);
- setgid(501);
+- (NSString *) firewire {
+ if (![indirect_ promptForSensitive:@"Firewire GUID"])
+ return nil;
+}
- if (![controller_ deliverMessage])
- [self performSelectorOnMainThread:@selector(showError) withObject:nil waitUntilDone:NO];
+- (NSString *) imei {
+ if (![indirect_ promptForSensitive:@"IMEI"])
+ return nil;
}
+#endif
-- (void) mailComposeControllerCompositionFinished:(MailComposeController *)controller {
- if ([controller_ needsDelivery])
- [NSThread detachNewThreadSelector:@selector(deliverMessage) toTarget:self withObject:nil];
++ (NSString *) webScriptNameForSelector:(SEL)selector {
+ if (selector == @selector(close))
+ return @"close";
+ else if (selector == @selector(getPackageById:))
+ return @"getPackageById";
+ else if (selector == @selector(setAutoPopup:))
+ return @"setAutoPopup";
+ else if (selector == @selector(setButtonImage:withStyle:toFunction:))
+ return @"setButtonImage";
+ else if (selector == @selector(setButtonTitle:withStyle:toFunction:))
+ return @"setButtonTitle";
+ else if (selector == @selector(setFinishHook:))
+ return @"setFinishHook";
+ else if (selector == @selector(setPopupHook:))
+ return @"setPopupHook";
+ else if (selector == @selector(setSpecial:))
+ return @"setSpecial";
+ else if (selector == @selector(setViewportWidth:))
+ return @"setViewportWidth";
+ else if (selector == @selector(supports:))
+ return @"supports";
+ else if (selector == @selector(stringWithFormat:arguments:))
+ return @"format";
+ else if (selector == @selector(localizedStringForKey:value:table:))
+ return @"localize";
+ else if (selector == @selector(du:))
+ return @"du";
+ else if (selector == @selector(statfs:))
+ return @"statfs";
else
- [self cancel];
+ return nil;
}
-- (id) initWithView:(UIView *)view delegate:(id)delegate url:(NSURL *)url {
- if ((self = [super initWithView:view delegate:delegate]) != nil) {
- controller_ = [[MailComposeController alloc] initForContentSize:[overlay_ bounds].size];
- [controller_ setDelegate:self];
- [controller_ initializeUI];
- [controller_ setupForURL:url];
++ (BOOL) isSelectorExcludedFromWebScript:(SEL)selector {
+ return [self webScriptNameForSelector:selector] == nil;
+}
- UIView *view([controller_ view]);
- [overlay_ addSubview:view];
- } return self;
+- (BOOL) supports:(NSString *)feature {
+ return [feature isEqualToString:@"window.open"];
+}
+
+- (Package *) getPackageById:(NSString *)id {
+ return [[Database sharedInstance] packageWithName:id];
+}
+
+- (NSArray *) statfs:(NSString *)path {
+ struct statfs stat;
+
+ if (path == nil || statfs([path UTF8String], &stat) == -1)
+ return nil;
+
+ return [NSArray arrayWithObjects:
+ [NSNumber numberWithUnsignedLong:stat.f_bsize],
+ [NSNumber numberWithUnsignedLong:stat.f_blocks],
+ [NSNumber numberWithUnsignedLong:stat.f_bfree],
+ nil];
+}
+
+- (NSNumber *) du:(NSString *)path {
+ NSNumber *value(nil);
+
+ int fds[2];
+ _assert(pipe(fds) != -1);
+
+ pid_t pid(ExecFork());
+ if (pid == 0) {
+ _assert(dup2(fds[1], 1) != -1);
+ _assert(close(fds[0]) != -1);
+ _assert(close(fds[1]) != -1);
+ /* XXX: this should probably not use du */
+ execl("/usr/libexec/cydia/du", "du", "-s", [path UTF8String], NULL);
+ exit(1);
+ _assert(false);
+ }
+
+ _assert(close(fds[1]) != -1);
+
+ if (FILE *du = fdopen(fds[0], "r")) {
+ char line[1024];
+ while (fgets(line, sizeof(line), du) != NULL) {
+ size_t length(strlen(line));
+ while (length != 0 && line[length - 1] == '\n')
+ line[--length] = '\0';
+ if (char *tab = strchr(line, '\t')) {
+ *tab = '\0';
+ value = [NSNumber numberWithUnsignedLong:strtoul(line, NULL, 0)];
+ }
+ }
+
+ fclose(du);
+ } else _assert(close(fds[0]));
+
+ int status;
+ wait:
+ if (waitpid(pid, &status, 0) == -1)
+ if (errno == EINTR)
+ goto wait;
+ else _assert(false);
+
+ return value;
+}
+
+- (void) close {
+ [indirect_ close];
+}
+
+- (void) setAutoPopup:(BOOL)popup {
+ [indirect_ setAutoPopup:popup];
+}
+
+- (void) setButtonImage:(NSString *)button withStyle:(NSString *)style toFunction:(id)function {
+ [indirect_ setButtonImage:button withStyle:style toFunction:function];
+}
+
+- (void) setButtonTitle:(NSString *)button withStyle:(NSString *)style toFunction:(id)function {
+ [indirect_ setButtonTitle:button withStyle:style toFunction:function];
+}
+
+- (void) setSpecial:(id)function {
+ [indirect_ setSpecial:function];
+}
+
+- (void) setFinishHook:(id)function {
+ [indirect_ setFinishHook:function];
+}
+
+- (void) setPopupHook:(id)function {
+ [indirect_ setPopupHook:function];
+}
+
+- (void) setViewportWidth:(float)width {
+ [indirect_ setViewportWidth:width];
+}
+
+- (NSString *) stringWithFormat:(NSString *)format arguments:(WebScriptObject *)arguments {
+ //NSLog(@"SWF:\"%@\" A:%@", format, [arguments description]);
+ unsigned count([arguments count]);
+ id values[count];
+ for (unsigned i(0); i != count; ++i)
+ values[i] = [arguments objectAtIndex:i];
+ return [[[NSString alloc] initWithFormat:format arguments:reinterpret_cast<va_list>(values)] autorelease];
+}
+
+- (NSString *) localizedStringForKey:(NSString *)key value:(NSString *)value table:(NSString *)table {
+ if (reinterpret_cast<id>(value) == [WebUndefined undefined])
+ value = nil;
+ if (reinterpret_cast<id>(table) == [WebUndefined undefined])
+ table = nil;
+ return [[NSBundle mainBundle] localizedStringForKey:key value:value table:table];
}
@end
/* }}} */
-#endif
-/* Confirmation View {{{ */
-bool DepSubstrate(const pkgCache::VerIterator &iterator) {
- if (!iterator.end())
- for (pkgCache::DepIterator dep(iterator.DependsList()); !dep.end(); ++dep) {
- if (dep->Type != pkgCache::Dep::Depends && dep->Type != pkgCache::Dep::PreDepends)
- continue;
- pkgCache::PkgIterator package(dep.TargetPkg());
- if (package.end())
- continue;
- if (strcmp(package.Name(), "mobilesubstrate") == 0)
- return true;
- }
+@interface CydiaBrowserView : BrowserView {
+ CydiaObject *cydia_;
+}
- return false;
+@end
+
+@implementation CydiaBrowserView
+
+- (void) dealloc {
+ [cydia_ release];
+ [super dealloc];
+}
+
+- (void) webView:(WebView *)sender didClearWindowObject:(WebScriptObject *)window forFrame:(WebFrame *)frame {
+ [super webView:sender didClearWindowObject:window forFrame:frame];
+ [window setValue:cydia_ forKey:@"cydia"];
+}
+
+- (NSURLRequest *) webView:(WebView *)sender resource:(id)identifier willSendRequest:(NSURLRequest *)request redirectResponse:(NSURLResponse *)redirectResponse fromDataSource:(WebDataSource *)source {
+ NSMutableURLRequest *copy = [request mutableCopy];
+
+ if (Machine_ != NULL)
+ [copy setValue:[NSString stringWithUTF8String:Machine_] forHTTPHeaderField:@"X-Machine"];
+ if (UniqueID_ != nil)
+ [copy setValue:UniqueID_ forHTTPHeaderField:@"X-Unique-ID"];
+
+ if (Role_ != nil)
+ [copy setValue:Role_ forHTTPHeaderField:@"X-Role"];
+
+ return copy;
+}
+
+- (id) initWithBook:(RVBook *)book forWidth:(float)width {
+ if ((self = [super initWithBook:book forWidth:width ofClass:[CydiaBrowserView class]]) != nil) {
+ cydia_ = [[CydiaObject alloc] initWithDelegate:indirect_];
+
+ WebView *webview([webview_ webView]);
+
+ Package *package([[Database sharedInstance] packageWithName:@"cydia"]);
+ NSString *application = package == nil ? @"Cydia" : [NSString
+ stringWithFormat:@"Cydia/%@",
+ [package installed]
+ ];
+
+ if (Product_ != nil)
+ application = [NSString stringWithFormat:@"%@ Version/%@", application, Product_];
+ if (Build_ != nil)
+ application = [NSString stringWithFormat:@"%@ Mobile/%@", application, Build_];
+ if (Safari_ != nil)
+ application = [NSString stringWithFormat:@"%@ Safari/%@", application, Safari_];
+
+ [webview setApplicationNameForUserAgent:application];
+ } return self;
}
+@end
+
@protocol ConfirmationViewDelegate
- (void) cancel;
- (void) confirm;
- (void) queue;
@end
-@interface ConfirmationView : BrowserView {
+@interface ConfirmationView : CydiaBrowserView {
_transient Database *database_;
UIActionSheet *essential_;
NSArray *changes_;
if (!remove)
essential_ = nil;
else if (Advanced_ || true) {
- NSString *parenthetical(CYLocalize("PARENTHETICAL"));
+ NSString *parenthetical(UCLocalize("PARENTHETICAL"));
essential_ = [[UIActionSheet alloc]
- initWithTitle:CYLocalize("REMOVING_ESSENTIALS")
+ initWithTitle:UCLocalize("REMOVING_ESSENTIALS")
buttons:[NSArray arrayWithObjects:
- [NSString stringWithFormat:parenthetical, CYLocalize("CANCEL_OPERATION"), CYLocalize("SAFE")],
- [NSString stringWithFormat:parenthetical, CYLocalize("FORCE_REMOVAL"), CYLocalize("UNSAFE")],
+ [NSString stringWithFormat:parenthetical, UCLocalize("CANCEL_OPERATION"), UCLocalize("SAFE")],
+ [NSString stringWithFormat:parenthetical, UCLocalize("FORCE_REMOVAL"), UCLocalize("UNSAFE")],
nil]
defaultButtonIndex:0
delegate:self
#ifndef __OBJC2__
[essential_ setDestructiveButton:[[essential_ buttons] objectAtIndex:0]];
#endif
- [essential_ setBodyText:CYLocalize("REMOVING_ESSENTIALS_EX")];
+ [essential_ setBodyText:UCLocalize("REMOVING_ESSENTIALS_EX")];
} else {
essential_ = [[UIActionSheet alloc]
- initWithTitle:CYLocalize("UNABLE_TO_COMPLY")
- buttons:[NSArray arrayWithObjects:CYLocalize("OKAY"), nil]
+ initWithTitle:UCLocalize("UNABLE_TO_COMPLY")
+ buttons:[NSArray arrayWithObjects:UCLocalize("OKAY"), nil]
defaultButtonIndex:0
delegate:self
context:@"unable"
];
- [essential_ setBodyText:CYLocalize("UNABLE_TO_COMPLY_EX")];
+ [essential_ setBodyText:UCLocalize("UNABLE_TO_COMPLY_EX")];
}
changes_ = [[NSArray alloc] initWithObjects:
}
- (NSString *) backButtonTitle {
- return CYLocalize("CONFIRM");
+ return UCLocalize("CONFIRM");
}
- (NSString *) leftButtonTitle {
- return [NSString stringWithFormat:CYLocalize("SLASH_DELIMITED"), CYLocalize("CANCEL"), CYLocalize("QUEUE")];
+ return [NSString stringWithFormat:UCLocalize("SLASH_DELIMITED"), UCLocalize("CANCEL"), UCLocalize("QUEUE")];
}
- (id) rightButtonTitle {
#if AlwaysReload || IgnoreInstall
return [super _rightButtonTitle];
#else
- return CYLocalize("CONFIRM");
+ return UCLocalize("CONFIRM");
#endif
}
[transition_ transition:6 toView:view_];
}
-- (void) alertSheet:(UIActionSheet *)sheet buttonClicked:(int)button {
- NSString *context([sheet context]);
-
- if ([context isEqualToString:@"error"])
- [sheet dismiss];
- else if ([context isEqualToString:@"conffile"]) {
- FILE *input = [database_ input];
-
- switch (button) {
- case 1:
- fprintf(input, "N\n");
- fflush(input);
- break;
- case 2:
- fprintf(input, "Y\n");
- fflush(input);
- break;
- default:
- _assert(false);
- }
-
- [sheet dismiss];
- }
-}
-
-- (void) closeButtonPushed {
- running_ = NO;
-
- switch (Finish_) {
- case 0:
- [self resetView];
- break;
-
- case 1:
- [delegate_ suspendWithAnimation:YES];
- break;
+- (void) _checkError {
+ if (_error->PendingError()) {
+ std::string error;
+ if (!_error->PopMessage(error))
+ _assert(false);
- case 2:
- system("launchctl stop com.apple.SpringBoard");
- break;
+ UIActionSheet *sheet = [[[UIActionSheet alloc]
+ initWithTitle:UCLocalize("ERROR")
+ buttons:[NSArray arrayWithObjects:UCLocalize("OKAY"), nil]
+ defaultButtonIndex:0
+ delegate:self
+ context:@"_error"
+ ] autorelease];
- case 3:
- system("launchctl unload "SpringBoard_"; launchctl load "SpringBoard_);
- break;
+ [sheet setBodyText:[NSString stringWithUTF8String:error.c_str()]];
+ [sheet popupAlertAnimated:YES];
- case 4:
- system("reboot");
- break;
+ return;
}
-}
-
-- (void) _retachThread {
- UINavigationItem *item = [navbar_ topItem];
- [item setTitle:CYLocalize("COMPLETE")];
-
- [overlay_ addSubview:close_];
- [progress_ removeFromSuperview];
- [status_ removeFromSuperview];
[delegate_ progressViewIsComplete:self];
if (Finish_ < 4) {
- FileFd file(SandboxTemplate_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- if (!(sandplate_ == sha1.Result()))
- Finish_ = 4;
- }
-
- if (Finish_ < 4) {
- FileFd file(NotifyConfig_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- if (!(notifyconf_ == sha1.Result()))
- Finish_ = 4;
+ FileFd file;
+ if (!file.Open(NotifyConfig_, FileFd::ReadOnly))
+ _error->Discard();
+ else {
+ MMap mmap(file, MMap::ReadOnly);
+ SHA1Summation sha1;
+ sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
+ if (!(notifyconf_ == sha1.Result()))
+ Finish_ = 4;
+ }
}
if (Finish_ < 3) {
- FileFd file(SpringBoard_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- if (!(springlist_ == sha1.Result()))
- Finish_ = 3;
+ FileFd file;
+ if (!file.Open(SpringBoard_, FileFd::ReadOnly))
+ _error->Discard();
+ else {
+ MMap mmap(file, MMap::ReadOnly);
+ SHA1Summation sha1;
+ sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
+ if (!(springlist_ == sha1.Result()))
+ Finish_ = 3;
+ }
}
switch (Finish_) {
- case 0: [close_ setTitle:CYLocalize("RETURN_TO_CYDIA")]; break;
- case 1: [close_ setTitle:CYLocalize("CLOSE_CYDIA")]; break;
- case 2: [close_ setTitle:CYLocalize("RESTART_SPRINGBOARD")]; break;
- case 3: [close_ setTitle:CYLocalize("RELOAD_SPRINGBOARD")]; break;
- case 4: [close_ setTitle:CYLocalize("REBOOT_DEVICE")]; break;
+ case 0: [close_ setTitle:UCLocalize("RETURN_TO_CYDIA")]; break;
+ case 1: [close_ setTitle:UCLocalize("CLOSE_CYDIA")]; break;
+ case 2: [close_ setTitle:UCLocalize("RESTART_SPRINGBOARD")]; break;
+ case 3: [close_ setTitle:UCLocalize("RELOAD_SPRINGBOARD")]; break;
+ case 4: [close_ setTitle:UCLocalize("REBOOT_DEVICE")]; break;
}
#define Cache_ "/User/Library/Caches/com.apple.mobile.installation.plist"
[delegate_ setStatusBarShowsProgress:NO];
}
+- (void) alertSheet:(UIActionSheet *)sheet buttonClicked:(int)button {
+ NSString *context([sheet context]);
+
+ if ([context isEqualToString:@"error"])
+ [sheet dismiss];
+ else if ([context isEqualToString:@"_error"]) {
+ [sheet dismiss];
+ [self _checkError];
+ } else if ([context isEqualToString:@"conffile"]) {
+ FILE *input = [database_ input];
+
+ switch (button) {
+ case 1:
+ fprintf(input, "N\n");
+ fflush(input);
+ break;
+ case 2:
+ fprintf(input, "Y\n");
+ fflush(input);
+ break;
+ default:
+ _assert(false);
+ }
+
+ [sheet dismiss];
+ }
+}
+
+- (void) closeButtonPushed {
+ running_ = NO;
+
+ switch (Finish_) {
+ case 0:
+ [self resetView];
+ break;
+
+ case 1:
+ [delegate_ suspendWithAnimation:YES];
+ break;
+
+ case 2:
+ system("launchctl stop com.apple.SpringBoard");
+ break;
+
+ case 3:
+ system("launchctl unload "SpringBoard_"; launchctl load "SpringBoard_);
+ break;
+
+ case 4:
+ system("reboot");
+ break;
+ }
+}
+
+- (void) _retachThread {
+ UINavigationItem *item = [navbar_ topItem];
+ [item setTitle:UCLocalize("COMPLETE")];
+
+ [overlay_ addSubview:close_];
+ [progress_ removeFromSuperview];
+ [status_ removeFromSuperview];
+
+ [self _checkError];
+}
+
- (void) _detachNewThreadData:(ProgressData *)data { _pooled
[[data target] performSelector:[data selector] withObject:[data object]];
[data release];
running_ = YES;
{
- FileFd file(SandboxTemplate_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- sandplate_ = sha1.Result();
- }
-
- {
- FileFd file(NotifyConfig_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- notifyconf_ = sha1.Result();
+ FileFd file;
+ if (!file.Open(NotifyConfig_, FileFd::ReadOnly))
+ _error->Discard();
+ else {
+ MMap mmap(file, MMap::ReadOnly);
+ SHA1Summation sha1;
+ sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
+ notifyconf_ = sha1.Result();
+ }
}
{
- FileFd file(SpringBoard_, FileFd::ReadOnly);
- MMap mmap(file, MMap::ReadOnly);
- SHA1Summation sha1;
- sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
- springlist_ = sha1.Result();
+ FileFd file;
+ if (!file.Open(SpringBoard_, FileFd::ReadOnly))
+ _error->Discard();
+ else {
+ MMap mmap(file, MMap::ReadOnly);
+ SHA1Summation sha1;
+ sha1.Add(reinterpret_cast<uint8_t *>(mmap.Data()), mmap.Size());
+ springlist_ = sha1.Result();
+ }
}
[transition_ transition:6 toView:overlay_];
detachNewThreadSelector:selector
toTarget:database_
withObject:nil
- title:CYLocalize("REPAIRING")
+ title:UCLocalize("REPAIRING")
];
}
UIActionSheet *sheet = [[[UIActionSheet alloc]
initWithTitle:(package == nil ? id : [package name])
- buttons:[NSArray arrayWithObjects:CYLocalize("OKAY"), nil]
+ buttons:[NSArray arrayWithObjects:UCLocalize("OKAY"), nil]
defaultButtonIndex:0
delegate:self
context:@"error"
//NSString *nfile = conffile_r[2];
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("CONFIGURATION_UPGRADE")
+ initWithTitle:UCLocalize("CONFIGURATION_UPGRADE")
buttons:[NSArray arrayWithObjects:
- CYLocalize("KEEP_OLD_COPY"),
- CYLocalize("ACCEPT_NEW_COPY"),
- // XXX: CYLocalize("SEE_WHAT_CHANGED"),
+ UCLocalize("KEEP_OLD_COPY"),
+ UCLocalize("ACCEPT_NEW_COPY"),
+ // XXX: UCLocalize("SEE_WHAT_CHANGED"),
nil]
defaultButtonIndex:0
delegate:self
context:@"conffile"
] autorelease];
- [sheet setBodyText:[NSString stringWithFormat:@"%@\n\n%@", CYLocalize("CONFIGURATION_UPGRADE_EX"), ofile]];
+ [sheet setBodyText:[NSString stringWithFormat:@"%@\n\n%@", UCLocalize("CONFIGURATION_UPGRADE_EX"), ofile]];
[sheet popupAlertAnimated:YES];
}
label = [source label];
trusted = [source trusted];
} else if ([[package id] isEqualToString:@"firmware"])
- label = CYLocalize("APPLE");
+ label = UCLocalize("APPLE");
else
- label = [NSString stringWithFormat:CYLocalize("SLASH_DELIMITED"), CYLocalize("UNKNOWN"), CYLocalize("LOCAL")];
+ label = [NSString stringWithFormat:UCLocalize("SLASH_DELIMITED"), UCLocalize("UNKNOWN"), UCLocalize("LOCAL")];
NSString *from(label);
NSString *section = [package simpleSection];
if (section != nil && ![section isEqualToString:label]) {
section = [[NSBundle mainBundle] localizedStringForKey:section value:nil table:@"Sections"];
- from = [NSString stringWithFormat:CYLocalize("PARENTHETICAL"), from, section];
+ from = [NSString stringWithFormat:UCLocalize("PARENTHETICAL"), from, section];
}
- from = [NSString stringWithFormat:CYLocalize("FROM"), from];
+ from = [NSString stringWithFormat:UCLocalize("FROM"), from];
source_ = [from retain];
if (NSString *purpose = [package primaryPurpose])
[mode isEqualToString:@"REMOVE"] || [mode isEqualToString:@"PURGE"] ? @"removing.png" : @"installing.png"
]];
- [status_ setText:[NSString stringWithFormat:CYLocalize("QUEUED_FOR"), CYLocalize(mode)]];
+ [status_ setText:[NSString stringWithFormat:UCLocalize("QUEUED_FOR"), UCLocalize(mode)]];
[status_ setColor:[UIColor colorWithCGColor:Blueish_]];
} else if ([package half]) {
[badge_ setImage:[UIImage applicationImageNamed:@"damaged.png"]];
- [status_ setText:CYLocalize("PACKAGE_DAMAGED")];
+ [status_ setText:UCLocalize("PACKAGE_DAMAGED")];
[status_ setColor:[UIColor redColor]];
} else {
[badge_ setImage:nil];
[self clearSection];
if (section == nil) {
- name_ = [CYLocalize("ALL_PACKAGES") retain];
+ name_ = [UCLocalize("ALL_PACKAGES") retain];
count_ = nil;
} else {
section_ = [section localized];
if (section_ != nil)
section_ = [section_ retain];
- name_ = [(section_ == nil ? CYLocalize("NO_SECTION") : section_) retain];
+ name_ = [(section_ == nil || [section_ length] == 0 ? UCLocalize("NO_SECTION") : section_) retain];
count_ = [[NSString stringWithFormat:@"%d", [section count]] retain];
if (editing_)
[self addSubview:list_];
UITableColumn *column = [[[UITableColumn alloc]
- initWithTitle:CYLocalize("NAME")
+ initWithTitle:UCLocalize("NAME")
identifier:@"name"
width:[self frame].size.width
] autorelease];
}
- (NSString *) title {
- return CYLocalize("INSTALLED_FILES");
+ return UCLocalize("INSTALLED_FILES");
}
- (NSString *) backButtonTitle {
- return CYLocalize("FILES");
+ return UCLocalize("FILES");
}
@end
/* }}} */
/* Package View {{{ */
-@interface PackageView : BrowserView {
+@interface PackageView : CydiaBrowserView {
_transient Database *database_;
Package *package_;
NSString *name_;
/* XXX: this is not safe at all... localization of /fail/ */
- (void) _clickButtonWithName:(NSString *)name {
- if ([name isEqualToString:CYLocalize("CLEAR")])
+ if ([name isEqualToString:UCLocalize("CLEAR")])
[delegate_ clearPackage:package_];
- else if ([name isEqualToString:CYLocalize("INSTALL")])
+ else if ([name isEqualToString:UCLocalize("INSTALL")])
[delegate_ installPackage:package_];
- else if ([name isEqualToString:CYLocalize("REINSTALL")])
+ else if ([name isEqualToString:UCLocalize("REINSTALL")])
[delegate_ installPackage:package_];
- else if ([name isEqualToString:CYLocalize("REMOVE")])
+ else if ([name isEqualToString:UCLocalize("REMOVE")])
[delegate_ removePackage:package_];
- else if ([name isEqualToString:CYLocalize("UPGRADE")])
+ else if ([name isEqualToString:UCLocalize("UPGRADE")])
[delegate_ installPackage:package_];
else _assert(false);
}
else {
NSMutableArray *buttons = [NSMutableArray arrayWithCapacity:(count + 1)];
[buttons addObjectsFromArray:buttons_];
- [buttons addObject:CYLocalize("CANCEL")];
+ [buttons addObject:UCLocalize("CANCEL")];
[delegate_ slideUp:[[[UIActionSheet alloc]
initWithTitle:nil
- (id) _rightButtonTitle {
int count = [buttons_ count];
- return count == 0 ? nil : count != 1 ? CYLocalize("MODIFY") : [buttons_ objectAtIndex:0];
+ return count == 0 ? nil : count != 1 ? UCLocalize("MODIFY") : [buttons_ objectAtIndex:0];
}
- (NSString *) backButtonTitle {
commercial_ = [package isCommercial];
if ([package_ mode] != nil)
- [buttons_ addObject:CYLocalize("CLEAR")];
+ [buttons_ addObject:UCLocalize("CLEAR")];
if ([package_ source] == nil);
else if ([package_ upgradableAndEssential:NO])
- [buttons_ addObject:CYLocalize("UPGRADE")];
- else if ([package_ installed] == nil)
- [buttons_ addObject:CYLocalize("INSTALL")];
+ [buttons_ addObject:UCLocalize("UPGRADE")];
+ else if ([package_ uninstalled])
+ [buttons_ addObject:UCLocalize("INSTALL")];
else
- [buttons_ addObject:CYLocalize("REINSTALL")];
- if ([package_ installed] != nil)
- [buttons_ addObject:CYLocalize("REMOVE")];
+ [buttons_ addObject:UCLocalize("REINSTALL")];
+ if (![package_ uninstalled])
+ [buttons_ addObject:UCLocalize("REMOVE")];
if (special_ != NULL) {
CGRect frame([webview_ frame]);
[list_ setDataSource:self];
UITableColumn *column = [[[UITableColumn alloc]
- initWithTitle:CYLocalize("NAME")
+ initWithTitle:UCLocalize("NAME")
identifier:@"name"
width:[self frame].size.width
] autorelease];
- (NSString *) sectionList:(UISectionList *)list titleForSection:(int)section {
switch (section + (offset_ == 0 ? 1 : 0)) {
- case 0: return CYLocalize("ENTERED_BY_USER");
- case 1: return CYLocalize("INSTALLED_BY_PACKAGE");
+ case 0: return UCLocalize("ENTERED_BY_USER");
+ case 1: return UCLocalize("INSTALLED_BY_PACKAGE");
default:
_assert(false);
defer = true;
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("SOURCE_WARNING")
- buttons:[NSArray arrayWithObjects:CYLocalize("ADD_ANYWAY"), CYLocalize("CANCEL"), nil]
+ initWithTitle:UCLocalize("SOURCE_WARNING")
+ buttons:[NSArray arrayWithObjects:UCLocalize("ADD_ANYWAY"), UCLocalize("CANCEL"), nil]
defaultButtonIndex:0
delegate:self
context:@"warning"
[self complete];
} else if (error_ != nil) {
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("VERIFICATION_ERROR")
- buttons:[NSArray arrayWithObjects:CYLocalize("OK"), nil]
+ initWithTitle:UCLocalize("VERIFICATION_ERROR")
+ buttons:[NSArray arrayWithObjects:UCLocalize("OK"), nil]
defaultButtonIndex:0
delegate:self
context:@"urlerror"
[sheet popupAlertAnimated:YES];
} else {
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("NOT_REPOSITORY")
- buttons:[NSArray arrayWithObjects:CYLocalize("OK"), nil]
+ initWithTitle:UCLocalize("NOT_REPOSITORY")
+ buttons:[NSArray arrayWithObjects:UCLocalize("OK"), nil]
defaultButtonIndex:0
delegate:self
context:@"trivial"
] autorelease];
- [sheet setBodyText:CYLocalize("NOT_REPOSITORY_EX")];
+ [sheet setBodyText:UCLocalize("NOT_REPOSITORY_EX")];
[sheet popupAlertAnimated:YES];
}
trivial_ = false;
hud_ = [[delegate_ addProgressHUD] retain];
- [hud_ setText:CYLocalize("VERIFYING_URL")];
+ [hud_ setText:UCLocalize("VERIFYING_URL")];
} break;
case 2:
[list_ setDataSource:self];
UITableColumn *column = [[UITableColumn alloc]
- initWithTitle:CYLocalize("NAME")
+ initWithTitle:UCLocalize("NAME")
identifier:@"name"
width:[self frame].size.width
];
] autorelease]];*/
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("ENTER_APT_URL")
- buttons:[NSArray arrayWithObjects:CYLocalize("ADD_SOURCE"), CYLocalize("CANCEL"), nil]
+ initWithTitle:UCLocalize("ENTER_APT_URL")
+ buttons:[NSArray arrayWithObjects:UCLocalize("ADD_SOURCE"), UCLocalize("CANCEL"), nil]
defaultButtonIndex:0
delegate:self
context:@"source"
}
- (NSString *) title {
- return CYLocalize("SOURCES");
+ return UCLocalize("SOURCES");
}
- (NSString *) leftButtonTitle {
- return [[list_ table] isRowDeletionEnabled] ? CYLocalize("ADD") : nil;
+ return [[list_ table] isRowDeletionEnabled] ? UCLocalize("ADD") : nil;
}
- (id) rightButtonTitle {
- return [[list_ table] isRowDeletionEnabled] ? CYLocalize("DONE") : CYLocalize("EDIT");
+ return [[list_ table] isRowDeletionEnabled] ? UCLocalize("DONE") : UCLocalize("EDIT");
}
- (UINavigationButtonStyle) rightButtonStyle {
}
- (NSString *) title {
- return CYLocalize("INSTALLED");
+ return UCLocalize("INSTALLED");
}
- (NSString *) backButtonTitle {
- return CYLocalize("PACKAGES");
+ return UCLocalize("PACKAGES");
}
- (id) rightButtonTitle {
- return Role_ != nil && [Role_ isEqualToString:@"Developer"] ? nil : expert_ ? CYLocalize("EXPERT") : CYLocalize("SIMPLE");
+ return Role_ != nil && [Role_ isEqualToString:@"Developer"] ? nil : expert_ ? UCLocalize("EXPERT") : UCLocalize("SIMPLE");
}
- (UINavigationButtonStyle) rightButtonStyle {
/* }}} */
/* Home View {{{ */
-@interface HomeView : BrowserView {
+@interface HomeView : CydiaBrowserView {
}
@end
- (void) _leftButtonClicked {
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("ABOUT_CYDIA")
- buttons:[NSArray arrayWithObjects:CYLocalize("CLOSE"), nil]
+ initWithTitle:UCLocalize("ABOUT_CYDIA")
+ buttons:[NSArray arrayWithObjects:UCLocalize("CLOSE"), nil]
defaultButtonIndex:0
delegate:self
context:@"about"
}
- (NSString *) leftButtonTitle {
- return CYLocalize("ABOUT");
+ return UCLocalize("ABOUT");
}
@end
/* }}} */
/* Manage View {{{ */
-@interface ManageView : BrowserView {
+@interface ManageView : CydiaBrowserView {
}
@end
@implementation ManageView
- (NSString *) title {
- return CYLocalize("MANAGE");
+ return UCLocalize("MANAGE");
}
- (void) _leftButtonClicked {
}
- (NSString *) leftButtonTitle {
- return CYLocalize("SETTINGS");
+ return UCLocalize("SETTINGS");
}
#if !AlwaysReload
- (id) _rightButtonTitle {
- return Queuing_ ? CYLocalize("QUEUE") : nil;
+ return Queuing_ ? UCLocalize("QUEUE") : nil;
}
- (UINavigationButtonStyle) rightButtonStyle {
@end
/* }}} */
-#include <BrowserView.m>
-
/* Cydia Book {{{ */
@interface CYBook : RVBook <
ProgressDelegate
[UIView endAnimations];
[indicator_ startAnimation];
- [prompt_ setText:CYLocalize("UPDATING_DATABASE")];
+ [prompt_ setText:UCLocalize("UPDATING_DATABASE")];
[progress_ setProgress:0];
updating_ = true;
];
}
-- (void) _update_ {
+- (void) alertSheet:(UIActionSheet *)sheet buttonClicked:(int)button {
+ NSString *context([sheet context]);
+
+ if ([context isEqualToString:@"refresh"])
+ [sheet dismiss];
+}
+
+- (void) _update_:(NSString *)error {
updating_ = false;
[indicator_ stopAnimation];
[UIView commitAnimations];
- [delegate_ performSelector:@selector(reloadData) withObject:nil afterDelay:0];
+ if (error == nil)
+ [delegate_ performSelector:@selector(reloadData) withObject:nil afterDelay:0];
+ else {
+ UIActionSheet *sheet = [[[UIActionSheet alloc]
+ initWithTitle:[NSString stringWithFormat:UCLocalize("COLON_DELIMITED"), UCLocalize("ERROR"), UCLocalize("REFRESH")]
+ buttons:[NSArray arrayWithObjects:
+ UCLocalize("OK"),
+ nil]
+ defaultButtonIndex:0
+ delegate:self
+ context:@"refresh"
+ ] autorelease];
+
+ [sheet setBodyText:error];
+ [sheet popupAlertAnimated:YES];
+
+ [self reloadButtons];
+ }
}
- (id) initWithFrame:(CGRect)frame database:(Database *)database {
[progress_ setStyle:0];
[overlay_ addSubview:progress_];
- cancel_ = [[UINavigationButton alloc] initWithTitle:CYLocalize("CANCEL") style:UINavigationButtonStyleHighlighted];
+ cancel_ = [[UINavigationButton alloc] initWithTitle:UCLocalize("CANCEL") style:UINavigationButtonStyleHighlighted];
[cancel_ addTarget:self action:@selector(_onCancel) forControlEvents:UIControlEventTouchUpInside];
CGRect frame = [cancel_ frame];
Status status;
status.setDelegate(self);
- [database_ updateWithStatus:status];
+ NSString *error([database_ updateWithStatus:status]);
[self
- performSelectorOnMainThread:@selector(_update_)
- withObject:nil
+ performSelectorOnMainThread:@selector(_update_:)
+ withObject:error
waitUntilDone:NO
];
}
- (void) setProgressError:(NSString *)error forPackage:(NSString *)id {
- [prompt_ setText:[NSString stringWithFormat:CYLocalize("COLON_DELIMITED"), CYLocalize("ERROR"), error]];
+ [prompt_ setText:[NSString stringWithFormat:UCLocalize("COLON_DELIMITED"), UCLocalize("ERROR"), error]];
}
- (void) setProgressTitle:(NSString *)title {
return !updating_;
}
-- (void) alertSheet:(UIActionSheet *)sheet buttonClicked:(int)button {
- [sheet dismiss];
-}
-
- (void) _setProgressTitle:(NSString *)title {
[prompt_ setText:title];
}
if (row == 0) {
section = nil;
name = nil;
- title = CYLocalize("ALL_PACKAGES");
+ title = UCLocalize("ALL_PACKAGES");
} else {
section = [filtered_ objectAtIndex:(row - 1)];
name = [section name];
- if (name != nil)
+ if (name != nil) {
+ name = [NSString stringWithString:name];
title = [[NSBundle mainBundle] localizedStringForKey:Simplify(name) value:nil table:@"Sections"];
- else {
+ } else {
name = @"";
- title = CYLocalize("NO_SECTION");
+ title = UCLocalize("NO_SECTION");
}
}
[transition_ transition:0 toView:list_];
UITableColumn *column = [[[UITableColumn alloc]
- initWithTitle:CYLocalize("NAME")
+ initWithTitle:UCLocalize("NAME")
identifier:@"name"
width:[self frame].size.width
] autorelease];
[*section addToCount];
_profile(SectionsView$reloadData$Filter)
- if (![package valid] || [package installed] != nil || ![package visible])
+ if (![package valid] || ![package uninstalled] || ![package visible])
continue;
_end
[section addToCount];
_profile(SectionsView$reloadData$Filter)
- if (![package valid] || [package installed] != nil || ![package visible])
+ if (![package valid] || ![package uninstalled] || ![package visible])
continue;
_end
}
- (NSString *) title {
- return editing_ ? CYLocalize("SECTION_VISIBILITY") : CYLocalize("INSTALL_BY_SECTION");
+ return editing_ ? UCLocalize("SECTION_VISIBILITY") : UCLocalize("INSTALL_BY_SECTION");
}
- (NSString *) backButtonTitle {
- return CYLocalize("SECTIONS");
+ return UCLocalize("SECTIONS");
}
- (id) rightButtonTitle {
- return [sections_ count] == 0 ? nil : editing_ ? CYLocalize("DONE") : CYLocalize("EDIT");
+ return [sections_ count] == 0 ? nil : editing_ ? UCLocalize("DONE") : UCLocalize("EDIT");
}
- (UINavigationButtonStyle) rightButtonStyle {
//[list_ setSectionListStyle:1];
UITableColumn *column = [[[UITableColumn alloc]
- initWithTitle:CYLocalize("NAME")
+ initWithTitle:UCLocalize("NAME")
identifier:@"name"
width:[self frame].size.width
] autorelease];
_trace();
for (Package *package in packages)
if (
- [package installed] == nil && [package valid] && [package visible] ||
+ [package uninstalled] && [package valid] && [package visible] ||
[package upgradableAndEssential:YES]
)
[packages_ addObject:package];
[packages_ radixSortUsingFunction:reinterpret_cast<SKRadixFunction>(&PackageChangesRadix) withContext:NULL];
_trace();
- Section *upgradable = [[[Section alloc] initWithName:CYLocalize("AVAILABLE_UPGRADES") localize:NO] autorelease];
- Section *ignored = [[[Section alloc] initWithName:CYLocalize("IGNORED_UPGRADES") localize:NO] autorelease];
+ Section *upgradable = [[[Section alloc] initWithName:UCLocalize("AVAILABLE_UPGRADES") localize:NO] autorelease];
+ Section *ignored = [[[Section alloc] initWithName:UCLocalize("IGNORED_UPGRADES") localize:NO] autorelease];
Section *section = nil;
NSDate *last = nil;
NSString *name;
if (seen == nil)
- name = CYLocalize("UNKNOWN");
+ name = UCLocalize("UNKNOWN");
else {
name = (NSString *) CFDateFormatterCreateStringWithDate(NULL, formatter, (CFDateRef) seen);
[name autorelease];
}
_profile(ChangesView$reloadData$Allocate)
- name = [NSString stringWithFormat:CYLocalize("NEW_AT"), name];
+ name = [NSString stringWithFormat:UCLocalize("NEW_AT"), name];
section = [[[Section alloc] initWithName:name row:offset localize:NO] autorelease];
[sections_ addObject:section];
_end
}
- (NSString *) leftButtonTitle {
- return [(CYBook *)book_ updating] ? nil : CYLocalize("REFRESH");
+ return [(CYBook *)book_ updating] ? nil : UCLocalize("REFRESH");
}
- (id) rightButtonTitle {
- return upgrades_ == 0 ? nil : [NSString stringWithFormat:CYLocalize("PARENTHETICAL"), CYLocalize("UPGRADE"), [NSString stringWithFormat:@"%u", upgrades_]];
+ return upgrades_ == 0 ? nil : [NSString stringWithFormat:UCLocalize("PARENTHETICAL"), UCLocalize("UPGRADE"), [NSString stringWithFormat:@"%u", upgrades_]];
}
- (NSString *) title {
- return CYLocalize("CHANGES");
+ return UCLocalize("CHANGES");
}
@end
- (NSString *) preferencesTable:(UIPreferencesTable *)table titleForGroup:(int)group {
switch (group) {
- case 0: return [NSString stringWithFormat:CYLocalize("PARENTHETICAL"), CYLocalize("ADVANCED_SEARCH"), CYLocalize("COMING_SOON")];
+ case 0: return [NSString stringWithFormat:UCLocalize("PARENTHETICAL"), UCLocalize("ADVANCED_SEARCH"), UCLocalize("COMING_SOON")];
default: _assert(false);
}
UIFont *font = [UIFont systemFontOfSize:16];
[field_ setFont:font];
- [field_ setPlaceholder:CYLocalize("SEARCH_EX")];
+ [field_ setPlaceholder:UCLocalize("SEARCH_EX")];
[field_ setDelegate:self];
[field_ setPaddingTop:5];
}
- (NSString *) backButtonTitle {
- return CYLocalize("SEARCH");
+ return UCLocalize("SEARCH");
}
- (void) setDelegate:(id)delegate {
case 0: {
UIPreferencesControlTableCell *cell([[[UIPreferencesControlTableCell alloc] init] autorelease]);
[cell setShowSelection:NO];
- [cell setTitle:CYLocalize("SHOW_ALL_CHANGES_EX")];
+ [cell setTitle:UCLocalize("SHOW_ALL_CHANGES_EX")];
return cell;
}
subscribedCell_ = [[UIPreferencesControlTableCell alloc] init];
[subscribedCell_ setShowSelection:NO];
- [subscribedCell_ setTitle:CYLocalize("SHOW_ALL_CHANGES")];
+ [subscribedCell_ setTitle:UCLocalize("SHOW_ALL_CHANGES")];
[subscribedCell_ setControl:subscribedSwitch_];
ignoredCell_ = [[UIPreferencesControlTableCell alloc] init];
[ignoredCell_ setShowSelection:NO];
- [ignoredCell_ setTitle:CYLocalize("IGNORE_UPGRADES")];
+ [ignoredCell_ setTitle:UCLocalize("IGNORE_UPGRADES")];
[ignoredCell_ setControl:ignoredSwitch_];
[table_ setDataSource:self];
}
- (NSString *) title {
- return CYLocalize("SETTINGS");
+ return UCLocalize("SETTINGS");
}
@end
/* Signature View {{{ */
-@interface SignatureView : BrowserView {
+@interface SignatureView : CydiaBrowserView {
_transient Database *database_;
NSString *package_;
}
int count = [broken_ count];
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:(count == 1 ? CYLocalize("HALFINSTALLED_PACKAGE") : [NSString stringWithFormat:CYLocalize("HALFINSTALLED_PACKAGES"), count])
+ initWithTitle:(count == 1 ? UCLocalize("HALFINSTALLED_PACKAGE") : [NSString stringWithFormat:UCLocalize("HALFINSTALLED_PACKAGES"), count])
buttons:[NSArray arrayWithObjects:
- CYLocalize("FORCIBLY_CLEAR"),
- CYLocalize("TEMPORARY_IGNORE"),
+ UCLocalize("FORCIBLY_CLEAR"),
+ UCLocalize("TEMPORARY_IGNORE"),
nil]
defaultButtonIndex:0
delegate:self
context:@"fixhalf"
] autorelease];
- [sheet setBodyText:CYLocalize("HALFINSTALLED_PACKAGE_EX")];
+ [sheet setBodyText:UCLocalize("HALFINSTALLED_PACKAGE_EX")];
[sheet popupAlertAnimated:YES];
} else if (!Ignored_ && [essential_ count] != 0) {
int count = [essential_ count];
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:(count == 1 ? CYLocalize("ESSENTIAL_UPGRADE") : [NSString stringWithFormat:CYLocalize("ESSENTIAL_UPGRADES"), count])
+ initWithTitle:(count == 1 ? UCLocalize("ESSENTIAL_UPGRADE") : [NSString stringWithFormat:UCLocalize("ESSENTIAL_UPGRADES"), count])
buttons:[NSArray arrayWithObjects:
- CYLocalize("UPGRADE_ESSENTIAL"),
- CYLocalize("COMPLETE_UPGRADE"),
- CYLocalize("TEMPORARY_IGNORE"),
+ UCLocalize("UPGRADE_ESSENTIAL"),
+ UCLocalize("COMPLETE_UPGRADE"),
+ UCLocalize("TEMPORARY_IGNORE"),
nil]
defaultButtonIndex:0
delegate:self
context:@"upgrade"
] autorelease];
- [sheet setBodyText:CYLocalize("ESSENTIAL_UPGRADE_EX")];
+ [sheet setBodyText:UCLocalize("ESSENTIAL_UPGRADE_EX")];
[sheet popupAlertAnimated:YES];
}
}
static bool loaded(false);
UIProgressHUD *hud([self addProgressHUD]);
- [hud setText:(loaded ? CYLocalize("RELOADING_DATA") : CYLocalize("LOADING_DATA"))];
+ [hud setText:(loaded ? UCLocalize("RELOADING_DATA") : UCLocalize("LOADING_DATA"))];
loaded = true;
[database_ yieldToSelector:@selector(reloadData) withObject:nil];
detachNewThreadSelector:@selector(update_)
toTarget:self
withObject:nil
- title:CYLocalize("UPDATING_SOURCES")
+ title:UCLocalize("UPDATING_SOURCES")
];
}
- (void) cancel {
[self slideUp:[[[UIActionSheet alloc]
initWithTitle:nil
- buttons:[NSArray arrayWithObjects:CYLocalize("CONTINUE_QUEUING"), CYLocalize("CANCEL_CLEAR"), nil]
+ buttons:[NSArray arrayWithObjects:UCLocalize("CONTINUE_QUEUING"), UCLocalize("CANCEL_CLEAR"), nil]
defaultButtonIndex:1
delegate:self
context:@"cancel"
detachNewThreadSelector:@selector(perform)
toTarget:database_
withObject:nil
- title:CYLocalize("RUNNING")
+ title:UCLocalize("RUNNING")
];
}
}
- (RVPage *) _pageForURL:(NSURL *)url withClass:(Class)_class {
- BrowserView *browser = [[[_class alloc] initWithBook:book_] autorelease];
+ CydiaBrowserView *browser = [[[_class alloc] initWithBook:book_] autorelease];
[browser loadURL:url];
return browser;
}
}
- (void) askForSettings {
- NSString *parenthetical(CYLocalize("PARENTHETICAL"));
+ NSString *parenthetical(UCLocalize("PARENTHETICAL"));
UIActionSheet *role = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("WHO_ARE_YOU")
+ initWithTitle:UCLocalize("WHO_ARE_YOU")
buttons:[NSArray arrayWithObjects:
- [NSString stringWithFormat:parenthetical, CYLocalize("USER"), CYLocalize("USER_EX")],
- [NSString stringWithFormat:parenthetical, CYLocalize("HACKER"), CYLocalize("HACKER_EX")],
- [NSString stringWithFormat:parenthetical, CYLocalize("DEVELOPER"), CYLocalize("DEVELOPER_EX")],
+ [NSString stringWithFormat:parenthetical, UCLocalize("USER"), UCLocalize("USER_EX")],
+ [NSString stringWithFormat:parenthetical, UCLocalize("HACKER"), UCLocalize("HACKER_EX")],
+ [NSString stringWithFormat:parenthetical, UCLocalize("DEVELOPER"), UCLocalize("DEVELOPER_EX")],
nil]
defaultButtonIndex:-1
delegate:self
context:@"role"
] autorelease];
- [role setBodyText:CYLocalize("ROLE_EX")];
+ [role setBodyText:UCLocalize("ROLE_EX")];
[role popupAlertAnimated:YES];
}
@"install-dn.png", kUIButtonBarButtonSelectedInfo,
[NSNumber numberWithInt:2], kUIButtonBarButtonTag,
self, kUIButtonBarButtonTarget,
- CYLocalize("SECTIONS"), kUIButtonBarButtonTitle,
+ UCLocalize("SECTIONS"), kUIButtonBarButtonTitle,
@"0", kUIButtonBarButtonType,
nil],
@"changes-dn.png", kUIButtonBarButtonSelectedInfo,
[NSNumber numberWithInt:3], kUIButtonBarButtonTag,
self, kUIButtonBarButtonTarget,
- CYLocalize("CHANGES"), kUIButtonBarButtonTitle,
+ UCLocalize("CHANGES"), kUIButtonBarButtonTitle,
@"0", kUIButtonBarButtonType,
nil],
@"manage-dn.png", kUIButtonBarButtonSelectedInfo,
[NSNumber numberWithInt:4], kUIButtonBarButtonTag,
self, kUIButtonBarButtonTarget,
- CYLocalize("MANAGE"), kUIButtonBarButtonTitle,
+ UCLocalize("MANAGE"), kUIButtonBarButtonTitle,
@"0", kUIButtonBarButtonType,
nil],
@"search-dn.png", kUIButtonBarButtonSelectedInfo,
[NSNumber numberWithInt:5], kUIButtonBarButtonTag,
self, kUIButtonBarButtonTarget,
- CYLocalize("SEARCH"), kUIButtonBarButtonTitle,
+ UCLocalize("SEARCH"), kUIButtonBarButtonTitle,
@"0", kUIButtonBarButtonType,
nil],
nil];
[self _reloadData];
else {
Queuing_ = true;
- [buttonbar_ setBadgeValue:CYLocalize("Q_D") forButton:4];
+ [buttonbar_ setBadgeValue:UCLocalize("Q_D") forButton:4];
[book_ reloadData];
}
Changed_ = true;
+ [sheet dismiss];
+
if (reset)
[self updateData];
else
[self finish];
-
- [sheet dismiss];
} else if ([context isEqualToString:@"upgrade"]) {
switch (button) {
case 1:
[window_ setUserInteractionEnabled:YES];
}
-- (void) openMailToURL:(NSURL *)url {
-// XXX: this makes me sad
-#if 0
- [[[MailToView alloc] initWithView:underlay_ delegate:self url:url] autorelease];
-#else
- [UIApp openURL:url];// asPanel:YES];
-#endif
-}
-
-- (void) clearFirstResponder {
- if (id responder = [window_ firstResponder])
- [responder resignFirstResponder];
-}
-
- (RVPage *) pageForPackage:(NSString *)name {
if (Package *package = [database_ packageWithName:name]) {
PackageView *view([self packageView]);
return view;
} else {
UIActionSheet *sheet = [[[UIActionSheet alloc]
- initWithTitle:CYLocalize("CANNOT_LOCATE_PACKAGE")
- buttons:[NSArray arrayWithObjects:CYLocalize("CLOSE"), nil]
+ initWithTitle:UCLocalize("CANNOT_LOCATE_PACKAGE")
+ buttons:[NSArray arrayWithObjects:UCLocalize("CLOSE"), nil]
defaultButtonIndex:0
delegate:self
context:@"missing"
] autorelease];
- [sheet setBodyText:[NSString stringWithFormat:CYLocalize("PACKAGE_CANNOT_BE_FOUND"), name]];
+ [sheet setBodyText:[NSString stringWithFormat:UCLocalize("PACKAGE_CANNOT_BE_FOUND"), name]];
[sheet popupAlertAnimated:YES];
return nil;
if (tag != NULL)
tag = 0;
+ NSString *href([url absoluteString]);
+ if ([href hasPrefix:@"apptapp://package/"])
+ return [self pageForPackage:[href substringFromIndex:18]];
+
NSString *scheme([[url scheme] lowercaseString]);
if (![scheme isEqualToString:@"cydia"])
return nil;
if ([path isEqualToString:@"/add-source"])
return [[[AddSourceView alloc] initWithBook:book_ database:database_] autorelease];
else if ([path isEqualToString:@"/storage"])
- return [self _pageForURL:[NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:@"storage" ofType:@"html"]] withClass:[BrowserView class]];
+ return [self _pageForURL:[NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:@"storage" ofType:@"html"]] withClass:[CydiaBrowserView class]];
else if ([path isEqualToString:@"/sources"])
return [[[SourceTable alloc] initWithBook:book_ database:database_] autorelease];
else if ([path isEqualToString:@"/packages"])
return [[[InstalledView alloc] initWithBook:book_ database:database_] autorelease];
else if ([path hasPrefix:@"/url/"])
- return [self _pageForURL:[NSURL URLWithString:[path substringFromIndex:5]] withClass:[BrowserView class]];
+ return [self _pageForURL:[NSURL URLWithString:[path substringFromIndex:5]] withClass:[CydiaBrowserView class]];
else if ([path hasPrefix:@"/launch/"])
[self launchApplicationWithIdentifier:[path substringFromIndex:8] suspended:NO];
else if ([path hasPrefix:@"/package-settings/"])
if (
readlink("/Applications", NULL, 0) == -1 && errno == EINVAL ||
readlink("/Library/Ringtones", NULL, 0) == -1 && errno == EINVAL ||
- readlink("/Library/Wallpaper", NULL, 0) == -1 && errno == EINVAL ||
+ readlink("/Library/Wallpaper", NULL, 0) == -1 && errno == EINVAL /*||
+ readlink("/usr/bin", NULL, 0) == -1 && errno == EINVAL*/ ||
readlink("/usr/include", NULL, 0) == -1 && errno == EINVAL ||
+ readlink("/usr/lib/pam", NULL, 0) == -1 && errno == EINVAL ||
readlink("/usr/libexec", NULL, 0) == -1 && errno == EINVAL ||
readlink("/usr/share", NULL, 0) == -1 && errno == EINVAL /*||
readlink("/var/lib", NULL, 0) == -1 && errno == EINVAL*/