尝试重定向STDERR以捕获iOS上的日志时应用程序挂起

时间:2015-06-03 14:17:54

标签: ios iphone ipad mobile stderr

我正在使用以下代码捕获设备的日志输出,以便能够将支持票据和200行的块发送到我的iOS应用中的服务器。

// This redirects stderr to pipe and handles it back in the main thread
-(void)redirectStandardErrorToAsyncMainDispatcher
{
    // Save reference to strerr
    stdoutDescriptor = dup(fileno(stderr));

    // Redirect stderr to pipe
    dup2([[self.logPipe fileHandleForWriting] fileDescriptor], fileno(stderr));

    // Add observer for pipe
    [[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(handleNotification:) name: NSFileHandleReadCompletionNotification object: self.logPipeHandleForReading] ;

    // Read pipe in background and notify
    [self.logPipeHandleForReading readInBackgroundAndNotify] ;
}

将其重定向到此方法:

-(void)handleNotification:(NSNotification*)notification
{
    // Read pipe in background and notify
    [self.logPipeHandleForReading readInBackgroundAndNotify] ;

    // Get the original string sent to stderr
    NSString *stdOutString = [[NSString alloc] initWithData: [[notification userInfo] objectForKey: NSFileHandleNotificationDataItem] encoding: NSASCIIStringEncoding] ;

    // Forward string to stdout
    [stdOutString writeToFile:@"/dev/stdout" atomically:NO encoding:NSUTF8StringEncoding error:nil];

    // Add string to log pool
    [self addStringToLogPool:stdOutString];
}

将stdout转发给stdout,然后转发到此方法,将其存储在日志池中并处理清理它们或将它们发送到服务器等等。

-(void)addStringToLogPool:(NSString*)stringToAdd
{
    // If log pool is enabled
    if (self.ticketLogPool &&
        self.logTrackingLogPool)
    {
        // Add string to log pool
        [self.ticketLogPool addObject:stringToAdd];
        [self.logTrackingLogPool addObject:stringToAdd];

        // If we have reached the maximum log pool size
        if (self.logTrackingLogPool.count > self.maximumLogPoolSize)
        {
            // If log tracking is enabled
            if (self.isLogTrackingEnabled)
            {
                // Send log pool content to server
                [self sendLogPoolContentToServer:self.logTrackingLogPool];

                // Clean log pool
                [self emptyLogPoolContent:self.logTrackingLogPool];

                // Increase log identifier
                self.logTransmissionNumber = [NSNumber numberWithLong:[self.logTransmissionNumber longValue] + 1];
            }
            // Otherwise, clean last row in queue
            else
            {
                [self.logTrackingLogPool removeObject:[self.logTrackingLogPool objectAtIndex:0]];
            }
        }

        // If we have reached the maximum log pool size
        if (self.ticketLogPool.count > self.maximumLogPoolSize)
        {
            [self.ticketLogPool removeObject:[self.ticketLogPool objectAtIndex:0]];
        }
    }
}

所有似乎都处于正常运转状态。唯一的问题是,当我在很短的时间内收到大量日志消息的垃圾邮件时,我完全停止了它们并且应用程序冻结了。不是崩溃或任何事情,只是冻结。就像管道充满了消息之前我可以清除它在后台阅读它。

可以做些什么来克服这个问题?

谢谢。

0 个答案:

没有答案