Re: [Pharo-dev] Nautilus memory leak/hog crashing Pharo
I'm trying to see if I could do it in a cleaner way, and I found it! On partial updates, AltBrowser is able to cleanly delete the node morphs because it sends #noteRemovalOfAll: aCollection to MorphTreeMorph, which has the selection testing and removal code. Which means changing MorphTreeMorph>>updateContentsWithPreviouslyExpanded: aNodeList nodeList := nil. self noteRemovalOfAll: self allNodeMorphs. "<-- Changed" (self nodeList isNil or: [ self nodeList isEmpty ]) ifTrue: [ nodeList := nil. ^ self emptySelection ]. self addSubmorphsFromNodeList: self currentNodelist previouslyExpanded: aNodeList It solves the problem. However, I don't like this that much overall, because delete is never sent to the node morphs themselves, and this seems very wrong to me. Thierry Le 30/06/2014 16:56, Goubier Thierry a écrit :
It would solve the selection kept while updating the full list, but it won't solve partial updates. You would also be apparently deselecting and reselecting when appending elements to the list.
Thierry
Le 30/06/2014 16:15, Nicolai Hess a écrit :
How about this change, if it rebuilds the whole list, we can savely remove the selection, or not?
MorphTreeMorph>> addSubmorphsFromNodeList: aNodeList previouslyExpanded: expandedNodeList | morphList | morphList := OrderedCollection new. self addMorphsTo: morphList from: aNodeList withExpandedItems: expandedNodeList atLevel: 0. self insertNewMorphs: morphList. self listManager emptySelection. "<--- added" self listManager updateSelectionFromModel. self roots do: [:r | r updateChildrenRecursively]. self updateColumnMorphs
2014-06-30 15:35 GMT+02:00 Goubier Thierry <thierry.goubier@cea.fr <mailto:thierry.goubier@cea.fr>>:
Ok, I have the test case showing the problem.
| c w t | c := ClassTreeExample new. w := c openOn: Collection. t := c dependents last. t expandAll. t selectAll. c updateList. t listManager selectedMorphList do: [ :each | self assert: ( t allNodeMorphs includes: each ) ]
Fail on the final assert. Switching to single selection hold the same error.
Interestingly, reselecting cleans the selectedMorphList.
| c w t | c := ClassTreeExample new. w := c openOn: Collection. t := c dependents last. t expandAll. t selectAll. c updateList. t setSelectedMorph: t allNodeMorphs first. t listManager selectedMorphList do: [ :each | self assert: ( t allNodeMorphs includes: each ) ]
This one has no error.
Changing the way Nautilus maintain the selection would work. Forcing selectedMorphList to be cleaned up on addition / removal in the list would be nice too (but possible update code can delete the node morphs by itself).
Thierry
Le 30/06/2014 10:15, Johan Brichau a écrit :
Hi Nicolai,
Do you have a method selected in the browser? As the memory leak happens via the selectedMorphs instvar, it requires a package to be selected (and maybe even a method).
Before and after the load. I do this and notice the increase.
Smalltalk garbageCollect. MorphTreeNodeMorph allInstances size.
It really only becomes problematic (i.e. out-of-mem) when you load large projects. Maybe MOOSE will qualify?
Yes, I was astonished as well when I noticed that every update was rebuilding the entire set of Morphs. It's the easiest solution of course but it does impose a lot of overhead. First, I will see how to solve that leaking problem. Then I will take a look at the update itself.
I can only spend some of my free time on this, so I will continue tonight.
best, Johan
On 30 Jun 2014, at 09:09, Nicolai Hess <nicolaihess@web.de <mailto:nicolaihess@web.de>> wrote:
2014-06-29 22:31 GMT+02:00 Johan Brichau <johan@inceptive.be <mailto:johan@inceptive.be>>:
On 27 Jun 2014, at 14:00, Goubier Thierry <thierry.goubier@cea.fr <mailto:thierry.goubier@cea.fr>> wrote:
It seems to depend on the Nautilus window state. If you've just opened it, then nothing seems to be amiss. If you start to select things in it, you start to see time spent in updateClassView, but why?
I just found that the instances are being kept by the MorphTreeListManager#__selectedMorphs instvar. So, that observation is correct: you need to have a package selected.
What seems to happen is that on every package load, the Nautilus package tree is updated (which means a PackageTreePackageNodeModel is created for each package in the image via #asNautilusNodeWithModel:). This update does not clear the selectedMorphs list and just this single reference seem to keep the entire package tree model and its Morphs in memory.
There were 496 morphs in the selectedMorphs list and when I cleaned that, all trailing Morphs and PackageNodeModelNodes (and all the other garbage) could be gc'ed.
On to investigating the growth of the selectedMorphs variable...
Johan
Yes, we had quite some bugs with this package tree update in the past. What I don't understand is, why is the whole tree removed and rebuild, maybe this is a common strategy in Morphic, update a list ore tree will always rebuild the whole morph structure? But it happens even if the structure is the same and just this little package/dirty package icon is updated.
Another issue is this "selected package/package selection". The tree (and for example the category list and/or method list" as well), stores the selection on multiple ways, in the model (PackageTreeNautilus), the UI (PackageTreeNautilusUi) and the treelist morph. Once as a SelectedTreeNode, a Package from Nautilus Model and once as a PackgeTreeSelection/__PackageTreeTagSelection. I find it pretty confusing.
BTW, I still can not reproduce this memory leak behavior. I tried this:
[ Gofer new smalltalkhubUser: 'ObjectProfile' project: 'Roassal2'; package: 'ConfigurationOfRoassal2'; load. (Smalltalk at: #ConfigurationOfRoassal2) load ] timeToRun.
with and without an open SystemBrowser. But the load time and memory consumption is the same.
Nicolai
-- Thierry Goubier CEA list Laboratoire des Fondations des Systèmes Temps Réel Embarqués 91191 Gif sur Yvette Cedex France Phone/Fax: +33 (0) 1 69 08 32 92 <tel:%2B33%20%280%29%201%2069%2008%2032%2092> / 83 95
-- Thierry Goubier CEA list Laboratoire des Fondations des Systèmes Temps Réel Embarqués 91191 Gif sur Yvette Cedex France Phone/Fax: +33 (0) 1 69 08 32 92 / 83 95
participants (1)
-
Goubier Thierry