Sam*_*Sam 6 memory-leaks external-accessory ios eaaccessory
我有一个连接到附件的应用程序,当我断开附件时,我创建的EASession是为了与附件通信泄漏.
当附件连接时,我收到通知,并检查EAAccessoryManager的附件集合,以查找具有使用某种协议的特定名称的附件.当我发现这个时,我使用代码为该附件创建了一个EASession对象:
-(void) openSession
{
... // finds accessory object
if (accessory)
{
[self closeSession];
session = [EASession alloc];
NSLog(@"alloc :: session retainCount: %i", session.retainCount);
[session initWithAccessory:accessory forProtocol:SmokeSignalsProtocolName];
NSLog(@"init :: session retainCount: %i", session.retainCount);
[[session inputStream] open];
[[session outputStream] open];
... // other logic (pump run loop, etc..)
}
}
-(void) closeSession
{
if (session)
{
[[session inputStream] close];
[[session outputStream] close];
[session release], session = nil;
}
}
Run Code Online (Sandbox Code Playgroud)
通常我在一行上有alloc和init,但我发现(将其分离出来)是alloc给出了+1保留计数(正如你所期望的那样)但是我iniWithAccessory:forProtocol:给它+3保留计数当我只会期望来自init方法的+2 retainCount.
泄漏仪器似乎也支持这一点:

一步一步看看泄漏仪器:
[???Accessory openSession]- 这是我分配新EASession的地方.[EAInputStream iniWithAccessory:forSession:]输入流将引用保存回拥有的会话.[EAOutputStream initWithAccessory:forSession:]输出流将引用保存回拥有的会话.[EASession iniWithAccessory:forProtocol:] 我不知道为什么这会增加EASession的保留计数.我认为这是我无法解释的额外保留计数的原因...不确定这应该如何平衡.这是Apple的错误,我需要release额外的时间来平衡事情....非常非常奇怪.[EAInputStream close] 清理上面的步骤#2[EAOutputStream close] 清理上面的步骤#3???Accessory closeSession]清除步骤#1以上1那么......为什么我泄漏了EASession对象?使用EASession对象不泄漏的正确方法是什么?
EADemo连接到配件,但它不会泄漏.出于好奇,我添加了一个额外的东西[_session retain]以使其泄漏,所以我可以在乐器中遵循它的malloc历史.看到我的应用程序的malloc历史记录中没有调用一些内部事件,这很有趣.

你可以看到这已经[EAAccessoryInternal removeSession:]召唤了3次.这在我的应用程序的malloc历史中从未调用过.我认为这是为什么我的EASession没有被发布的关键...
小智 1
我知道这个讨论现在已经很老了,但我最近使用 ARC 等遇到了完全相同的问题,我发现解决这个问题的一种方法是不关闭输入或输出流。只需有一个类来处理所有输入等,并根据请求将数据转发到应用程序的其他部分。您可以重新分配初始化 EASession 对象,而不会受到 XCode 的投诉,因此我假设旧的 EASession 已释放,因为我的应用程序不再引用它。不过我还没有检查过泄漏情况。