Please, help me to understand, why reference count is growth on each concatenation? I am returning the same object in overloaded sub, and expecting, that refcount will stay untouched. But, seems, that perl cloning and storing object somewhere every time. Why and how I can avoid this?
Also, I am expecting, that object will be destroyed just after exiting scope, but due to non-zero references count it destroyed only on global destruction phase. This is looks like a memory leak.
#!/usr/bin/env perl
use strict;
use warnings;
use Devel::Refcount qw[refcount];
package AAA {
use Devel::Refcount qw[refcount];
use overload
'.' => sub {
print 'CONCAT, REFCOUNT: ', refcount( $_[0] ), "\n";
# return AAA->new;
return $_[0];
},
fallback => 0;
sub new { return bless {}, $_[0] }
sub DESTROY { print "DESTROY\n" }
}
print "--- start\n";
{
my $o = AAA->new;
my $s = '1' . ( '2' . ( '3' . ( '4' . ( '5' . $o ) ) ) );
print "--- exit scope\n";
print 'REFCOUNT: ', refcount($o), "\n";
}
print "--- end\n";
1;
Tested under
Output
--- start
CONCAT, REFCOUNT: 1
CONCAT, REFCOUNT: 3
CONCAT, REFCOUNT: 5
CONCAT, REFCOUNT: 7
CONCAT, REFCOUNT: 9
--- exit scope
REFCOUNT: 6
--- end
DESTROY
Just like the delayed DESTROY
message, adding a weak ref to the object indicates a leak. The leak appears to have been introduced in Perl 5.28.
use strict;
use warnings;
use Scalar::Util qw( weaken );
package AAA {
use overload
'.' => sub { $_[0] },
fallback => 0;
sub new { return bless {}, $_[0] }
sub DESTROY { print "DESTROY\n" }
}
my $w;
{
my $o = AAA->new;
weaken($w = $o);
my $s = '1' . ( '2' . ( '3' . ( '4' . ( '5' . $o ) ) ) );
print "Exiting scope...\n";
}
print "leak!\n" if defined($w);
#use Devel::Peek;
#Dump($w);
print "Global destruction...\n";
Output (before 5.28):
Exiting scope...
DESTROY
Global destruction...
Output (5.28.0 and 5.28.1):
Exiting scope...
leak!
Global destruction...
DESTROY
Please report using the perlbug
command line utility.The bug report can be found here.
It has been fixed in 5.30. It might be fixed in 5.28.2.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With