问题描述
我有一个用C ++编写的大型程序,并使用Inline :: CPP从Perl执行。该代码似乎占用了大量内存,因此我假设某种程度上存在泄漏。我编写了以下代码,该代码再现了同样的问题,但是要简单得多。当我循环执行代码1,000,000次以测试代码的性能时,我发现了泄漏。这个简单的Perl脚本使用828MiB,而我的完整程序使用1.3GiB。
我已经尝试了很多方法,例如对代码中的各个变量使用SvREFCNT_dec
,newRV_noinc
,sv_free
和sv_2mortal
,但是我没有能够降低内存使用量。
这是我的示例代码:
use Data::Dumper;
print Dumper test ();
use Inline 'CPP' => << 'CPP';
#include <array>
using namespace std;
AV *array_to_av (const array<int,3> &v)
{
AV *array = newAV ();
for (int i : v) {
av_push (array,newSViv (i));
}
return array;
}
SV *test_leak ()
{
HV *hash = newHV ();
AV *array1 = array_to_av ({1,2,3});
AV *array2 = array_to_av ({1,3});
AV *array3 = array_to_av ({1,3});
SV *value1 = newRV_noinc ((SV *)(array1));
SV *value2 = newRV_noinc ((SV *)(array2));
SV *value3 = newRV_noinc ((SV *)(array3));
hv_stores (hash,"Test1",value1);
hv_stores (hash,"Test2",value2);
hv_stores (hash,"Test3",value3);
return newRV_noinc ((SV *)(hash));
}
SV *test ()
{
SV *hash;
for (int i = 0; i < 1000000; i++) {
hash = test_leak ();
}
return hash;
}
CPP
sleep 10;
解决方法
您需要释放for
循环中未返回到Perl脚本的哈希。此循环:
for (int i = 0; i < 1000000; i++) {
hash = test_leak ();
}
应该是这样的:
for (int i = 0; i < 1000000; i++) {
hash = test_leak ();
SvREFCNT_dec(hash); // Free the memory not returned to Perl
}
hash = test_leak(); // The final hashref is returned to Perl