sw/source/core/inc/flowfrm.hxx | 34 ++++++++++++++++++++++++++++++++++ sw/source/core/layout/flowfrm.cxx | 23 +++++++++-------------- sw/source/core/layout/layact.cxx | 8 +++++++- 3 files changed, 50 insertions(+), 15 deletions(-)
New commits: commit 9857c6390212e16dd9f26b47b4afc5d33b5242ef Author: Caolán McNamara <caol...@redhat.com> Date: Tue Mar 31 17:14:19 2015 +0100 crashtest: crash on layout of novell622972-2.html Change-Id: I49be59a9b9cdda8f80b6579f393be0a99f231833 diff --git a/sw/source/core/inc/flowfrm.hxx b/sw/source/core/inc/flowfrm.hxx index 8a87a8a..59bafa4 100644 --- a/sw/source/core/inc/flowfrm.hxx +++ b/sw/source/core/inc/flowfrm.hxx @@ -62,6 +62,7 @@ class SwFlowFrm friend inline void TableSplitRecalcUnlock( SwFlowFrm * ); // #i44049# friend class SwObjectFormatterTxtFrm; + friend class JoinLockGuard; // TblSel is allowed to reset the follow-bit friend inline void UnsetFollow( SwFlowFrm *pFlow ); @@ -234,6 +235,39 @@ inline bool SwFlowFrm::IsFwdMoveAllowed() { return m_rThis.GetIndPrev() != 0; } + +//use this to protect a SwLayoutFrm for a given scope from getting merged with +//its neighbour and thus deleted +class JoinLockGuard +{ +private: + SwFlowFrm *m_pFlow; + bool m_bOldJoinLocked; +public: + //JoinLock pParent for the lifetime of the Cut/Paste call, etc. to avoid + //SwSectionFrm::MergeNext removing the pParent we're trying to reparent + //into + JoinLockGuard(SwLayoutFrm* pFrm) + { + m_pFlow = SwFlowFrm::CastFlowFrm(pFrm); + if (m_pFlow) + { + m_bOldJoinLocked = m_pFlow->IsJoinLocked(); + m_pFlow->LockJoin(); + } + else + { + m_bOldJoinLocked = false; + } + } + + ~JoinLockGuard() + { + if (m_pFlow && !m_bOldJoinLocked) + m_pFlow->UnlockJoin(); + } +}; + #endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/core/layout/flowfrm.cxx b/sw/source/core/layout/flowfrm.cxx index cb54c52..b9b5537 100644 --- a/sw/source/core/layout/flowfrm.cxx +++ b/sw/source/core/layout/flowfrm.cxx @@ -574,23 +574,18 @@ void SwFlowFrm::MoveSubTree( SwLayoutFrm* pParent, SwFrm* pSibling ) SwPageFrm *pOldPage = m_rThis.FindPageFrm(); - //JoinLock pParent for the lifetime of the Cut/Paste call to avoid - //SwSectionFrm::MergeNext removing the pParent we're trying to reparent - //into - bool bOldJoinLocked(false); - SwFlowFrm *pParentFlow = SwFlowFrm::CastFlowFrm(pParent); - if (pParentFlow) + SwLayoutFrm *pOldParent; + bool bInvaLay; + { - bOldJoinLocked = pParentFlow->IsJoinLocked(); - pParentFlow->LockJoin(); + //JoinLock pParent for the lifetime of the Cut/Paste call to avoid + //SwSectionFrm::MergeNext removing the pParent we're trying to reparent + //into + JoinLockGuard aJoinGuard(pParent); + pOldParent = CutTree( &m_rThis ); + bInvaLay = PasteTree( &m_rThis, pParent, pSibling, pOldParent ); } - SwLayoutFrm *pOldParent = CutTree( &m_rThis ); - const bool bInvaLay = PasteTree( &m_rThis, pParent, pSibling, pOldParent ); - - if (pParentFlow && !bOldJoinLocked) - pParentFlow->UnlockJoin(); - // If, by cutting & pasting, an empty SectionFrm came into existence, it should // disappear automatically. SwSectionFrm *pSct; diff --git a/sw/source/core/layout/layact.cxx b/sw/source/core/layout/layact.cxx index 0455e34..dbc90fd 100644 --- a/sw/source/core/layout/layact.cxx +++ b/sw/source/core/layout/layact.cxx @@ -1239,7 +1239,13 @@ bool SwLayAction::FormatLayout( SwLayoutFrm *pLay, bool bAddRect ) aOldRect = static_cast<SwPageFrm*>(pLay)->GetBoundRect(); } - pLay->Calc(); + { + //JoinLock pParent for the lifetime of the Calc call to avoid + //SwSectionFrm::MergeNext removing the pLay we're trying to Format + JoinLockGuard aJoinGuard(pLay); + pLay->Calc(); + } + if ( aOldFrame != pLay->Frm() ) bChanged = true;
_______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits