Specifically when the Collection is used for a Detailref property (e.g. Jobs->Steps), it should not keep a reference to the parent's ScopeItems. Reference cycles cause Perl's primitive reference-count based garbage collector to leak memory.
Signed-off-by: Francois Gouget fgouget@codeweavers.com --- testbot/lib/ObjectModel/Collection.pm | 9 +++++++++ 1 file changed, 9 insertions(+)
diff --git a/testbot/lib/ObjectModel/Collection.pm b/testbot/lib/ObjectModel/Collection.pm index c3bc438c..a9ec9958 100644 --- a/testbot/lib/ObjectModel/Collection.pm +++ b/testbot/lib/ObjectModel/Collection.pm @@ -43,6 +43,7 @@ require Exporter; @ISA = qw(Exporter); @EXPORT_OK = qw(&new &ComputeMasterKey);
+use Scalar::Util qw(weaken); use ObjectModel::BackEnd; use ObjectModel::Item; use ObjectModel::PropertyDescriptor; @@ -96,6 +97,14 @@ sub new($$$$$;$$@) Filters => {}, AllScopeItems => $AllScopeItems || {}, Items => undef}; + if ($AllScopeItems) + { + # Avoid memory cycles in case Items have Detailref properties: + # ParentCollection{AllScopeItems} --> ParentItem + # ParentItem --DetailrefProperty--> DetailCollection + # DetailCollection{AllScopeItems} == ParentCollection{AllScopeItems} + weaken($self->{AllScopeItems}); + } $self = bless $self, $class; $self->_initialize(@_); return $self;