Skip to content

Commit

Permalink
Make sure to suspend the logging on app suspension
Browse files Browse the repository at this point in the history
Failing to do so might trigger ios/macos killing our app with 0xdeadl0cc
because the file logger uses flock to serialize writes.
Holding any lockfiles during app suspension is disallowed by ios.
  • Loading branch information
tmolitor-stud-tu committed Nov 20, 2024
1 parent 8e23499 commit 5f5ad7e
Show file tree
Hide file tree
Showing 3 changed files with 54 additions and 25 deletions.
2 changes: 2 additions & 0 deletions Monal/Classes/HelperTools.h
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,8 @@ void swizzle(Class c, SEL orig, SEL new);
+(void) installExceptionHandler;
+(int) pendingCrashreportCount;
+(void) flushLogsWithTimeout:(double) timeout;
+(void) signalSuspension;
+(void) signalResumption;
+(void) __attribute__((noreturn)) MLAssertWithText:(NSString*) text andUserData:(id _Nullable) additionalData andFile:(const char* const) file andLine:(int) line andFunc:(const char* const) func;
+(void) __attribute__((noreturn)) handleRustPanicWithText:(NSString*) text andBacktrace:(NSString*) backtrace;
+(void) __attribute__((noreturn)) throwExceptionWithName:(NSString*) name reason:(NSString*) reason userInfo:(NSDictionary* _Nullable) userInfo;
Expand Down
28 changes: 28 additions & 0 deletions Monal/Classes/HelperTools.m
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,8 @@ -(void) swizzled_setObject:(id) value forKey:(NSString*) defaultName;
static char _origProfilePath[1024] = "";
static char _profilePath[1024] = "";
static NSObject* _isAppExtensionLock = nil;
static NSObject* _suspensionHandlingLock = nil;
static BOOL _suspensionHandlingIsSuspended = NO;
static NSMutableDictionary* _versionInfoCache;
static MLStreamRedirect* _stdoutRedirector = nil;
static MLStreamRedirect* _stderrRedirector = nil;
Expand Down Expand Up @@ -383,6 +385,8 @@ @implementation HelperTools

+(void) initialize
{
_suspensionHandlingLock = [NSObject new];
_suspensionHandlingIsSuspended = NO;
_isAppExtensionLock = [NSObject new];
_versionInfoCache = [NSMutableDictionary new];

Expand Down Expand Up @@ -2084,6 +2088,30 @@ +(void) flushLogsWithTimeout:(double) timeout
[MLUDPLogger flushWithTimeout:timeout];
}

+(void) signalSuspension
{
DDLogVerbose(@"Suspending logger queue...");
[HelperTools flushLogsWithTimeout:0.100];
@synchronized(_suspensionHandlingLock) {
dispatch_suspend([DDLog loggingQueue]);
_suspensionHandlingIsSuspended = YES;
}
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
}

+(void) signalResumption
{
@synchronized(_suspensionHandlingLock) {
if(_suspensionHandlingIsSuspended)
{
DDLogVerbose(@"Resuming logger queue...");
dispatch_resume([DDLog loggingQueue]);
_suspensionHandlingIsSuspended = NO;
}
}
}

+(void) configureXcodeLogging
{
//only start console logger
Expand Down
49 changes: 24 additions & 25 deletions Monal/Classes/MonalAppDelegate.m
Original file line number Diff line number Diff line change
Expand Up @@ -368,6 +368,9 @@ -(void) updateUnread

-(BOOL) application:(UIApplication*) application willFinishLaunchingWithOptions:(NSDictionary*) launchOptions
{
//resume logging and other core tasks
[HelperTools signalResumption];

DDLogInfo(@"App launching with options: %@", launchOptions);

//init IPC and ProcessLock
Expand Down Expand Up @@ -639,6 +642,9 @@ -(void) windowHandling:(NSNotification*) notification
}
else if([notification.name isEqualToString:@"NSWindowDidBecomeKeyNotification"])
{
//resume logging and other core tasks
[HelperTools signalResumption];

DDLogInfo(@"Window got focus (key window)...");
[MLProcessLock lock];
@synchronized(self) {
Expand Down Expand Up @@ -1134,6 +1140,9 @@ -(void) prepareForFreeze:(NSNotification*) notification

-(void) applicationWillEnterForeground:(UIApplication*) application
{
//resume logging and other core tasks
[HelperTools signalResumption];

DDLogInfo(@"Entering FG");
[MLProcessLock lock];

Expand Down Expand Up @@ -1239,6 +1248,7 @@ -(void) applicationWillTerminate:(UIApplication *)application
[[MLXMPPManager sharedInstance] disconnectAll];
DDLogInfo(@"|~~| T E R M I N A T E D |~~|");
[DDLog flushLog];
[HelperTools flushLogsWithTimeout:0.025];
}
}

Expand Down Expand Up @@ -1447,11 +1457,7 @@ -(void) checkIfBackgroundTaskIsStillNeeded
[DDLog flushLog];
}
else
{
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
[HelperTools flushLogsWithTimeout:0.100];
}
[HelperTools signalSuspension];
}];
}
}
Expand Down Expand Up @@ -1508,11 +1514,7 @@ -(void) addBackgroundTask
[[UIApplication sharedApplication] endBackgroundTask:task];

if(stopped)
{
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
[HelperTools flushLogsWithTimeout:0.100];
}
[HelperTools signalSuspension];
}
}];
}
Expand Down Expand Up @@ -1571,15 +1573,14 @@ -(void) handleBackgroundProcessingTask:(BGTask*) task
[task setTaskCompletedWithSuccess:!background];

if(stopped)
{
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
[HelperTools flushLogsWithTimeout:0.100];
}
[HelperTools signalSuspension];
}
}];
};

//resume logging and other core tasks
[HelperTools signalResumption];

//only proceed with our BGTASK if the NotificationServiceExtension is not running
[MLProcessLock lock];
[[IPC sharedInstance] sendMessage:@"Monal.disconnectAll" withData:nil to:@"NotificationServiceExtension"];
Expand Down Expand Up @@ -1679,15 +1680,14 @@ -(void) handleBackgroundRefreshingTask:(BGTask*) task
[task setTaskCompletedWithSuccess:!background];

if(stopped)
{
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
[HelperTools flushLogsWithTimeout:0.100];
}
[HelperTools signalSuspension];
}
}];
};

//resume logging and other core tasks
[HelperTools signalResumption];

//only proceed with our BGTASK if the NotificationServiceExtension is not running
[MLProcessLock lock];
[[IPC sharedInstance] sendMessage:@"Monal.disconnectAll" withData:nil to:@"NotificationServiceExtension"];
Expand Down Expand Up @@ -1828,6 +1828,9 @@ -(void) connectIfNecessaryWithOptions:(NSDictionary*) options

-(void) incomingWakeupWithCompletionHandler:(void (^)(UIBackgroundFetchResult result)) completionHandler
{
//resume logging and other core tasks
[HelperTools signalResumption];

if(![HelperTools isInBackground])
{
DDLogWarn(@"Ignoring incomingWakeupWithCompletionHandler: because app is in FG!");
Expand Down Expand Up @@ -1901,11 +1904,7 @@ -(void) incomingWakeupWithCompletionHandler:(void (^)(UIBackgroundFetchResult re
completionHandler(UIBackgroundFetchResultFailed);

if(stopped)
{
DDLogVerbose(@"Posting kMonalIsFreezed notification now...");
[[NSNotificationCenter defaultCenter] postNotificationName:kMonalIsFreezed object:nil];
[HelperTools flushLogsWithTimeout:0.100];
}
[HelperTools signalSuspension];

//trigger disconnect if we are idle and no timer is blocking us now
if(self->_bgTask != UIBackgroundTaskInvalid || self->_bgProcessing != nil || self->_bgRefreshing != nil)
Expand Down

0 comments on commit 5f5ad7e

Please sign in to comment.