我在我的 iOS 应用程序中遇到了 EPIPE 问题,并且它没有被 @try/@catch/@finally 块捕获。我怎样才能捕捉到这个信号(SIGPIPE,可能)......
我在我的应用程序中构建了一个“网络代理”,它将处理某些类型的 URL - 在这种错误情况下,似乎远程端(也在我的应用程序中,但隐藏在 iOS 库中)关闭了它的套接字端. 我没有收到通知(我应该吗?有什么我应该在 NSFileHandle 注册的东西可能对这里有帮助吗?)。
我已经将此代理基于 Matt Gallagher 放在一起的 HTTPServer(可在此处获得),问题出在HTTPRequestHandler
他放在一起的类的子类中。这是代码(此代码等效startResponse
于基类中的方法):
-(void)proxyTS:(SSProxyTSResource *)proxyTS didReceiveResource:(NSData *)resource
{
NSLog(@"[%@ %@]", NSStringFromClass([self class]), NSStringFromSelector(_cmd));
CFHTTPMessageRef response =
CFHTTPMessageCreateResponse(kCFAllocatorDefault, 200, NULL, kCFHTTPVersion1_1);
CFHTTPMessageSetHeaderFieldValue(response,
(CFStringRef)@"Content-Type",
(__bridge CFStringRef)s_MIMEtype);
CFHTTPMessageSetHeaderFieldValue(response,
(CFStringRef)@"Connection",
(CFStringRef)@"close");
CFHTTPMessageSetBody(response,
(__bridge CFDataRef)resource);
CFDataRef headerData = CFHTTPMessageCopySerializedMessage(response);
@try
{
NSLog(@" -> writing %u bytes to filehandle...",[((__bridge NSData *)headerData) length]);
[self.fileHandle writeData:(__bridge NSData *)headerData];
}
@catch (NSException *exception)
{
// Ignore the exception, it normally just means the client
// closed the connection from the other end.
}
@finally
{
NSLog(@" *ding*");
CFRelease(headerData);
CFRelease(response);
[self.server closeHandler:self];
}
}
这是崩溃时控制台日志中显示的内容:
Jan 15 14:55:10 AWT-NoTouch-iPhone-1 Streamer[1788] <Warning>: [SSProxyTSResponseHandler proxyTS:didReceiveResource:]
Jan 15 14:55:10 iPhone-1 Streamer[1788] <Warning>: -> writing 261760 bytes to filehandle...
Jan 15 14:55:11 iPhone-1 com.apple.launchd[1] (UIKitApplication:com.XXX.Streamer[0xf58][1788]) <Warning>: (UIKitApplication:com.XXX.Streamer[0xf58]) Exited abnormally: Broken pipe: 13
似乎因为另一端关闭了管道write()
失败了,所以如果有人能指出我如何发现它已经关闭而不尝试向它写入数据,或者任何使它不会崩溃的程序,那将是非常有帮助。