diff --git a/core/cont/src/TList.cxx b/core/cont/src/TList.cxx index 0089d2e29c3727a000b9e453a9e34742dec8a45c..344d61678d622c749b57fd2897b1a477b8af81c9 100644 --- a/core/cont/src/TList.cxx +++ b/core/cont/src/TList.cxx @@ -68,6 +68,7 @@ #include "TList.h" #include "TClass.h" +#include "TROOT.h" #include <string> namespace std {} using namespace std; @@ -351,6 +352,16 @@ void TList::Clear(Option_t *option) return; } + // In some case, for example TParallelCoord, a list (the pad's list of + // primitives) will contain both the container and the containees + // (the TParallelCoorVar) but if the Clear is being called from + // the destructor of the container of this list, one of the first + // thing done will be the remove the container (the pad) for the + // list (of Primitives of the canvas) that was connecting it + // (indirectly) to the list of cleanups. + // So let's temporarily add the current list and remove it later. + bool needRegister = fFirst && TROOT::Initialized() && !gROOT->GetListOfCleanups()->FindObject(this); + if (needRegister) gROOT->GetListOfCleanups()->Add(this); while (fFirst) { TObjLink *tlk = fFirst; fFirst = fFirst->Next(); @@ -365,6 +376,7 @@ void TList::Clear(Option_t *option) } delete tlk; } + if (needRegister) ROOT::GetROOT()->GetListOfCleanups()->Remove(this); fFirst = fLast = fCache = 0; fSize = 0; Changed(); @@ -385,6 +397,16 @@ void TList::Delete(Option_t *option) if (slow) { + // In some case, for example TParallelCoord, a list (the pad's list of + // primitives) will contain both the container and the containees + // (the TParallelCoorVar) but if the Clear is being called from + // the destructor of the container of this list, one of the first + // thing done will be the remove the container (the pad) for the + // list (of Primitives of the canvas) that was connecting it + // (indirectly) to the list of cleanups. + // So let's temporarily add the current list and remove it later. + bool needRegister = fFirst && TROOT::Initialized() && !gROOT->GetListOfCleanups()->FindObject(this); + if (needRegister) gROOT->GetListOfCleanups()->Add(this); while (fFirst) { TObjLink *tlk = fFirst; fFirst = fFirst->Next(); @@ -397,6 +419,7 @@ void TList::Delete(Option_t *option) delete tlk; } + if (needRegister) ROOT::GetROOT()->GetListOfCleanups()->Remove(this); fFirst = fLast = fCache = 0; fSize = 0; diff --git a/core/cont/src/TObjArray.cxx b/core/cont/src/TObjArray.cxx index 1a4d16495f27929f077e6aa5f6c44018fb3f50af..0336f5970e29ba2cc46351857209979099347b38 100644 --- a/core/cont/src/TObjArray.cxx +++ b/core/cont/src/TObjArray.cxx @@ -330,11 +330,23 @@ void TObjArray::Delete(Option_t *) { // Remove all objects from the array AND delete all heap based objects. - for (Int_t i = 0; i < fSize; i++) + // In some case, for example TParallelCoord, a list (the pad's list of + // primitives) will contain both the container and the containees + // (the TParallelCoorVar) but if the Clear is being called from + // the destructor of the container of this list, one of the first + // thing done will be the remove the container (the pad) for the + // list (of Primitives of the canvas) that was connecting it + // (indirectly) to the list of cleanups. + // So let's temporarily add the current list and remove it later. + bool needRegister = fSize && TROOT::Initialized() && !gROOT->GetListOfCleanups()->FindObject(this); + if (needRegister) gROOT->GetListOfCleanups()->Add(this); + for (Int_t i = 0; i < fSize; i++) { if (fCont[i] && fCont[i]->IsOnHeap()) { TCollection::GarbageCollect(fCont[i]); fCont[i] = 0; } + } + if (needRegister) ROOT::GetROOT()->GetListOfCleanups()->Remove(this); Init(fSize, fLowerBound); }