我有一个用于iPadOS的DriverKit驱动程序.它工作得很好,但静态分析器正在标记一个我不理解的可能的泄漏.标记的代码位于驱动程序类本身中:

void IMPL(CDCDriver, ReadComplete)
{
    // Simply trampolines back to USBCDCInterface where the read is actually handled
    IOBufferMemoryDescriptor *readDataBuffer = ivars->cdcInterface->readData(status, actualByteCount, completionTimestamp);
    if (actualByteCount > 0) {
        os_log(OS_LOG_DEFAULT, "[Driver] Got %u bytes of data!", actualByteCount);
        if (ivars->client != nullptr) {
            ivars->client->dataWasReceived(readDataBuffer, actualByteCount);
        }
    }
}  // [!] Potential leak of an object stored into 'readDataBuffer'

Screenshot of static analyzer results

根据分析器,在方法的第一行调用readData()返回类型为IOBufferMemoryDescriptorOSObject,保留计数为+1.但是,该方法是这样实现的:

IOBufferMemoryDescriptor *USBCDCInterface::readData(IOReturn status,
                                                    uint32_t actualByteCount,
                                                    uint64_t completionTimestamp)
{
    pollForData();
    return readDataBuffer;
}

这里,readDataBufferUSBCDCInterface的成员变量,在驱动程序通过调用IOUSBHostInterface::CreateIOBuffer()启动时创建:

IOBufferMemoryDescriptor *readDataBuffer = nullptr;
result = dataInterface->CreateIOBuffer(kIOMemoryDirectionIn, 256, &readDataBuffer);
if (result != kIOReturnSuccess) {
    return result;
}
this->readDataBuffer = readDataBuffer;

我对OSObject(及其子类)的理解是,它使用的引用计数机制非常类似于NSObject.创建它,例如使用CreateIOBuffer(),应该会产生一个保留计数为+1的对象.创建它的USBCDCInterface实例拥有它,因此当它处理完它时应该是release()(在USBCDCInterface::free()中).简单地从readData()返回它不应该转移所有权,释放它也不应该是该方法的调用者的责任.值得注意的是,在CDCDriver::ReadComplete()的末尾对对象调用release()会导致驱动程序崩溃,正如我所预期的那样,这让我认为这是分析器的假阳性.

要么我的理解有缺陷,从USBCDCInterface::readData()返回该对象的某些方面(按照惯例或其他方式)迫使调用者释放它(尽管这样做会再次导致驱动程序崩溃),要么这是分析器部分的错误肯定.

如果这是objc/cocoa,我猜可能是我的方法的命名导致分析器假定readData()方法有效地转移了所有权(就像-copy+alloc方法),但是我找不到任何这样的命名约定的文档,我也不能弄清楚OSObject方法是否/如何用它们的内存管理语义进行注释.

有没有人能提供一些见解?

推荐答案

你应该继续"如果这是Objective-C/Cocoa"的 idea ,直到它的合乎逻辑的结论:OSObjectfollows the same convention重新计算为Objective-C和CoreFoundation的.你有两个 Select :

Ios相关问答推荐

我想在expo 中使用useSafeAreaInsets来获取paddingbottom,但我得到了一个错误

在iOS 17脉冲符号效果不起作用的情况下制作UIBarButtonItem动画(没有UIImageView)

由于代码签名时出错,无法在iOS设备上发布iOS Maui Build

SWIFT根据地球坐标修改 node 旋转

当文本为空时,具有垂直轴的SwiftUI文本字段不会与FirstTextBaseline对齐

核心媒体基础知识,了解 CMSampleBuffer、CMBlockBuffer 和 CMSampleBufferGetAudioBufferListWithRetainedBlockBuffer

在我的 M1 上出现 Architecture arm64 问题,因此我无法运行我的旧项目

使用 SceneKit 从 CapturedRoom.walls 重新创建 RoomPlan

expo EAS build (iOS) 在 Pod 安装步骤中失败 (SDK45 & 46)

如何将单个按钮传递到自定义 ConfirmationDialog

UITableView 页脚,停止浮动内容

NSURLConnection 的 Xcode 4 警告未使用表达式结果

ARKit vs. ARCore vs. Vuforia vs. D'Fusion Mobile vs. Layar SDK

无论我将构建版本或应用程序版本更改为什么,都会出现 ITEMS-4238冗余二进制上传错误

没有 Mac 的 Xamarin Visual Studio IOS 开发?

如何在 OS X 或 iOS(不使用格式塔)中确定运行时的操作系统版本?

如何找出用于构建 *.ipa 文件的配置文件?

iOS Swift - 获取当前本地时间和日期时间戳

iOS7 UITextView contentsize.height 替代

iOS 7 应用程序图标、启动图像和命名约定,同时保留 iOS 6 图标