accessibility/source/extended/accessibletabbarbase.cxx | 2 include/svx/svdedtv.hxx | 3 - sd/source/filter/xml/sdxmlwrp.cxx | 3 - sd/source/ui/docshell/docshell.cxx | 10 ++++ svx/source/svdraw/svdedtv.cxx | 39 ++++++++++------- 5 files changed, 38 insertions(+), 19 deletions(-)
New commits: commit 3d59018b1ed816b4399cad4c2c4818cf25d4f4a1 Author: Michael Stahl <[email protected]> Date: Fri Jun 30 16:13:06 2017 +0200 tdf#108833 sd: don't unconditionally enable Undo after import Change-Id: Id637e649ccf3782658832d909b3a7150a0606229 diff --git a/sd/source/filter/xml/sdxmlwrp.cxx b/sd/source/filter/xml/sdxmlwrp.cxx index 38ef1d3f6341..4eed0b02cc38 100644 --- a/sd/source/filter/xml/sdxmlwrp.cxx +++ b/sd/source/filter/xml/sdxmlwrp.cxx @@ -453,6 +453,7 @@ bool SdXMLFilter::Import( ErrCode& nError ) comphelper::getProcessComponentContext(); SdDrawDocument* pDoc = mrDocShell.GetDoc(); + bool const bWasUndo(pDoc->IsUndoEnabled()); pDoc->EnableUndo(false); pDoc->NewOrLoadCompleted( NEW_DOC ); pDoc->CreateFirstPages(); @@ -769,7 +770,7 @@ bool SdXMLFilter::Import( ErrCode& nError ) fixupOutlinePlaceholderNumberingDepths(pDoc); - pDoc->EnableUndo(true); + pDoc->EnableUndo(bWasUndo); mrDocShell.ClearUndoBuffer(); return nRet == ERRCODE_NONE; } commit b2b085441dc79fb78607dbf1969c12a40db58214 Author: Michael Stahl <[email protected]> Date: Fri Jun 30 15:23:15 2017 +0200 accessibility: fix horrible memory leak in AccessibleTabBarBase Reproducing tdf#108833 failed because applying the Master Page takes > 2 hours; the time is spent calling vcl::Window listeners, of which there were some 39525 after a couple minutes, almost all of which AccessibleTabBarBase. AccessibleTabBarBase::WindowEventListener() has an inverted condition that suppresses the event that is generated from TabBar::Clear() and thus when DrawViewShell::ResetActualPage() calls Clear() no AccessibleTabBarPage is removed but then the InsertPage() calls create duplicate objects that again register as listeners. The condition is obviously inverted given the CVS commit message: 1.2.88.1 log @#135353# do not pass VCLEVENT_TABBAR_PAGEREMOVED (all) to objects other than AccessibleTabBarPageList @ text a69 8 if( ( pWinEvent->GetId() == VCLEVENT_TABBAR_PAGEREMOVED ) && ( (sal_uInt16)(sal_IntPtr) pWinEvent->GetData() == TAB_PAGE_NOTFOUND ) && ( dynamic_cast< AccessibleTabBarPageList *> (this) != NULL ) ) { return 0; } Change-Id: I2a3b86bbd0f0251a966f41b316a3b313517df24f diff --git a/accessibility/source/extended/accessibletabbarbase.cxx b/accessibility/source/extended/accessibletabbarbase.cxx index e1cec85dee48..af42864d3149 100644 --- a/accessibility/source/extended/accessibletabbarbase.cxx +++ b/accessibility/source/extended/accessibletabbarbase.cxx @@ -46,7 +46,7 @@ IMPL_LINK( AccessibleTabBarBase, WindowEventListener, VclWindowEvent&, rEvent, v if( ( rEvent.GetId() == VclEventId::TabbarPageRemoved ) && ( (sal_uInt16)reinterpret_cast<sal_IntPtr>(rEvent.GetData()) == TabBar::PAGE_NOT_FOUND ) && - ( dynamic_cast< AccessibleTabBarPageList *> (this) != nullptr ) ) + (dynamic_cast<AccessibleTabBarPageList *>(this) == nullptr)) { return; } commit a54ba50db2c341f0f0e47d77dbe64a6e588bc911 Author: Michael Stahl <[email protected]> Date: Fri Jun 30 12:43:21 2017 +0200 tdf#108863 svx: fix use-after-free in SdrEditView::DeleteMarkedObj() The sdr::ViewSelection has multiple vectors with pointers to the same SdrObjects, and those are only cleared in sdr::ViewSelection::SetEdgesOfMarkedNodesDirty(), so deleting SdrObjects that are marked must be delayed until after that is called. Change-Id: I7ab18cb2116164a71dce29bf10eca974061ab424 diff --git a/include/svx/svdedtv.hxx b/include/svx/svdedtv.hxx index 81c680f1c085..039f56cae89b 100644 --- a/include/svx/svdedtv.hxx +++ b/include/svx/svdedtv.hxx @@ -154,7 +154,8 @@ protected: // Removes all objects of the MarkList from their ObjLists including Undo. // The entries in rMark remain. - void DeleteMarkedList(const SdrMarkList& rMark); // DeleteMarked -> DeleteMarkedList + // @return a list of objects that must be deleted after the outermost EndUndo + std::vector<SdrObject *> DeleteMarkedList(SdrMarkList const& rMark); // DeleteMarked -> DeleteMarkedList // Check possibilities of all marked objects virtual void CheckPossibilities(); diff --git a/svx/source/svdraw/svdedtv.cxx b/svx/source/svdraw/svdedtv.cxx index 0382ffc77659..f3d5a046de14 100644 --- a/svx/source/svdraw/svdedtv.cxx +++ b/svx/source/svdraw/svdedtv.cxx @@ -678,8 +678,9 @@ void SdrEditView::ForceMarkedObjToAnotherPage() } } -void SdrEditView::DeleteMarkedList(const SdrMarkList& rMark) +std::vector<SdrObject*> SdrEditView::DeleteMarkedList(SdrMarkList const& rMark) { + std::vector<SdrObject*> ret; if (rMark.GetMarkCount()!=0) { rMark.ForceSort(); @@ -733,10 +734,8 @@ void SdrEditView::DeleteMarkedList(const SdrMarkList& rMark) if( !bUndo ) { - if( bIs3D ) - aRemoved3DObjects.push_back( pObj ); // may be needed later - else - SdrObject::Free(pObj); + // tdf#108863 don't delete objects before EndUndo() + ret.push_back(pObj); } } @@ -746,21 +745,22 @@ void SdrEditView::DeleteMarkedList(const SdrMarkList& rMark) delete aUpdaters.back(); aUpdaters.pop_back(); } - - if( !bUndo ) - { - // now delete removed scene objects - while(!aRemoved3DObjects.empty()) - { - SdrObject::Free( aRemoved3DObjects.back() ); - aRemoved3DObjects.pop_back(); - } - } } if( bUndo ) EndUndo(); } + return ret; +} + +static void lcl_LazyDelete(std::vector<SdrObject*> & rLazyDelete) +{ + // now delete removed scene objects + while (!rLazyDelete.empty()) + { + SdrObject::Free( rLazyDelete.back() ); + rLazyDelete.pop_back(); + } } void SdrEditView::DeleteMarkedObj() @@ -775,6 +775,7 @@ void SdrEditView::DeleteMarkedObj() BrkAction(); BegUndo(ImpGetResStr(STR_EditDelete),GetDescriptionOfMarkedObjects(),SdrRepeatFunc::Delete); + std::vector<SdrObject*> lazyDeleteObjects; // remove as long as something is selected. This allows to schedule objects for // removal for a next run as needed while(GetMarkedObjectCount()) @@ -835,7 +836,11 @@ void SdrEditView::DeleteMarkedObj() // original stuff: remove selected objects. Handle clear will // do something only once - DeleteMarkedList(GetMarkedObjectList()); + auto temp(DeleteMarkedList(GetMarkedObjectList())); + for (auto p : temp) + { + lazyDeleteObjects.push_back(p); + } GetMarkedObjectListWriteAccess().Clear(); maHdlList.Clear(); @@ -865,6 +870,8 @@ void SdrEditView::DeleteMarkedObj() // end undo and change messaging moved at the end EndUndo(); MarkListHasChanged(); + + lcl_LazyDelete(lazyDeleteObjects); } void SdrEditView::CopyMarkedObj() commit 495284716f49072e432b8425944cc67dfe0df0e0 Author: Michael Stahl <[email protected]> Date: Fri Jun 30 12:39:26 2017 +0200 tdf#108863 sd: disable Undo earlier if no Undo Steps If 0 Undo Steps, the Undo is disabled by a timer somewhere calling SfxShell::SetUndoManager(). This seems a bit risky, so disable it already when the sd::UndoManager is created. Change-Id: I9caf14fe32251d1f92cb5fa0683838316275eab3 diff --git a/sd/source/ui/docshell/docshell.cxx b/sd/source/ui/docshell/docshell.cxx index fa35e3a9808b..1ae312469225 100644 --- a/sd/source/ui/docshell/docshell.cxx +++ b/sd/source/ui/docshell/docshell.cxx @@ -18,6 +18,11 @@ */ #include "DrawDocShell.hxx" + +#include <officecfg/Office/Common.hxx> + +#include <unotools/configmgr.hxx> + #include <vcl/svapp.hxx> #include <sfx2/docfac.hxx> @@ -108,6 +113,11 @@ void DrawDocShell::Construct( bool bClipboard ) SetBaseModel( new SdXImpressDocument( this, bClipboard ) ); SetPool( &mpDoc->GetItemPool() ); mpUndoManager = new sd::UndoManager; + if (!utl::ConfigManager::IsAvoidConfig() + && officecfg::Office::Common::Undo::Steps::get() < 1) + { + mpUndoManager->EnableUndo(false); // tdf#108863 disable if 0 steps + } mpDoc->SetSdrUndoManager( mpUndoManager ); mpDoc->SetSdrUndoFactory( new sd::UndoFactory ); UpdateTablePointers(); _______________________________________________ Libreoffice-commits mailing list [email protected] https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits
