最小的 CoreML 预测泄漏内存
Minimal CoreML Prediction Leaking Memory
我在使用 CoreML 预测时发生内存泄漏(应用程序内存正在增加)。
我找不到任何我可能遗漏的正在发布的文档或示例。
在我的真实项目中我禁用了 ARC,但这里没有(所以编译器不允许我手动释放任何东西,所以我想我试过的那些东西不需要它)
我已将其减少到 a minimal case available on github。但这是其中的 99%(存储库只有模型和额外的项目资产,以及更多的错误检查 - 没有错误,预测运行良好,但由于 Whosebug 而减少)
#import <Cocoa/Cocoa.h>
#import "SsdMobilenet.h"
#include <string>
#include <iostream>
uint8_t ImageBytes[300*300*4];
CVPixelBufferRef MakePixelBuffer(size_t Width,size_t Height)
{
auto* Pixels = ImageBytes;
auto BytesPerRow = Width * 4;
CVPixelBufferRef PixelBuffer = nullptr;
auto Result = CVPixelBufferCreateWithBytes( nullptr, Width, Height, kCVPixelFormatType_32BGRA, Pixels, BytesPerRow, nullptr, nullptr, nullptr, &PixelBuffer );
return PixelBuffer;
}
int main(int argc, const char * argv[])
{
auto* Pixels = MakePixelBuffer(300,300);
SsdMobilenet* ssd = nullptr;
for ( auto i=0; i<10000; i++ )
{
if ( !ssd )
{
ssd = [[SsdMobilenet alloc] init];
}
auto* Output = [ssd predictionFromPreprocessor__sub__0:Pixels error:nullptr];
}
return 0;
}
有什么我应该清除、释放、释放、解除分配的吗?
我试过释放 ssd 并在每次迭代时重新创建它,但这没有帮助。
在 HighSierra 10.13.6 上,xcode 10.1 (10B61)。
泄漏发生在 2011 imac(无金属,CPU 执行)和 2013 Retina MBP(在 GPU 上运行)以及其他型号,而不仅仅是 SSDMobileNet。
编辑 1:查看仪器,使用 Generations/Snapshots,看起来确实是输出泄漏,但我不能 dealloc
或 release
,所以我可能还有其他原因需要做什么来释放结果?
<non-object>
是 CoreML 深处 apply_convulution_layer()
调用中的所有分配。
感谢@Matthijs-Hollemans,在禁用 ARC 的情况下使用 NSAutoReleasePool
,这不会泄漏。 (我也可以自动释放 SSD,但这种特殊组合会保持预先分配的 SSD 持久化)。
我没有 ARC/AutoReferenceCounting 版本的解决方案,因为 NSAutoReleasePool
不可用。
int main(int argc, const char * argv[])
{
auto* Pixels = MakePixelBuffer(300,300);
SsdMobilenet* ssd = [[SsdMobilenet alloc] init];
//SsdMobilenet* ssd = nullptr;
for ( auto i=0; i<10000; i++ )
{
NSAutoreleasePool* pool= [[NSAutoreleasePool alloc]init];
if ( !ssd )
{
ssd = [[SsdMobilenet alloc] init];
}
auto* Output = [ssd predictionFromPreprocessor__sub__0:Pixels error:nullptr];
//[Output release];
//[ssd release];
//ssd = nullptr;
[pool drain];
}
return 0;
}
我在使用 CoreML 预测时发生内存泄漏(应用程序内存正在增加)。 我找不到任何我可能遗漏的正在发布的文档或示例。 在我的真实项目中我禁用了 ARC,但这里没有(所以编译器不允许我手动释放任何东西,所以我想我试过的那些东西不需要它)
我已将其减少到 a minimal case available on github。但这是其中的 99%(存储库只有模型和额外的项目资产,以及更多的错误检查 - 没有错误,预测运行良好,但由于 Whosebug 而减少)
#import <Cocoa/Cocoa.h>
#import "SsdMobilenet.h"
#include <string>
#include <iostream>
uint8_t ImageBytes[300*300*4];
CVPixelBufferRef MakePixelBuffer(size_t Width,size_t Height)
{
auto* Pixels = ImageBytes;
auto BytesPerRow = Width * 4;
CVPixelBufferRef PixelBuffer = nullptr;
auto Result = CVPixelBufferCreateWithBytes( nullptr, Width, Height, kCVPixelFormatType_32BGRA, Pixels, BytesPerRow, nullptr, nullptr, nullptr, &PixelBuffer );
return PixelBuffer;
}
int main(int argc, const char * argv[])
{
auto* Pixels = MakePixelBuffer(300,300);
SsdMobilenet* ssd = nullptr;
for ( auto i=0; i<10000; i++ )
{
if ( !ssd )
{
ssd = [[SsdMobilenet alloc] init];
}
auto* Output = [ssd predictionFromPreprocessor__sub__0:Pixels error:nullptr];
}
return 0;
}
有什么我应该清除、释放、释放、解除分配的吗? 我试过释放 ssd 并在每次迭代时重新创建它,但这没有帮助。
在 HighSierra 10.13.6 上,xcode 10.1 (10B61)。
泄漏发生在 2011 imac(无金属,CPU 执行)和 2013 Retina MBP(在 GPU 上运行)以及其他型号,而不仅仅是 SSDMobileNet。
编辑 1:查看仪器,使用 Generations/Snapshots,看起来确实是输出泄漏,但我不能 dealloc
或 release
,所以我可能还有其他原因需要做什么来释放结果?
<non-object>
是 CoreML 深处 apply_convulution_layer()
调用中的所有分配。
感谢@Matthijs-Hollemans,在禁用 ARC 的情况下使用 NSAutoReleasePool
,这不会泄漏。 (我也可以自动释放 SSD,但这种特殊组合会保持预先分配的 SSD 持久化)。
我没有 ARC/AutoReferenceCounting 版本的解决方案,因为 NSAutoReleasePool
不可用。
int main(int argc, const char * argv[])
{
auto* Pixels = MakePixelBuffer(300,300);
SsdMobilenet* ssd = [[SsdMobilenet alloc] init];
//SsdMobilenet* ssd = nullptr;
for ( auto i=0; i<10000; i++ )
{
NSAutoreleasePool* pool= [[NSAutoreleasePool alloc]init];
if ( !ssd )
{
ssd = [[SsdMobilenet alloc] init];
}
auto* Output = [ssd predictionFromPreprocessor__sub__0:Pixels error:nullptr];
//[Output release];
//[ssd release];
//ssd = nullptr;
[pool drain];
}
return 0;
}