diff options
author | Caolán McNamara <caolanm@redhat.com> | 2015-10-05 13:32:06 +0100 |
---|---|---|
committer | Caolán McNamara <caolanm@redhat.com> | 2015-10-05 20:30:58 +0100 |
commit | 91ff5501892f8c3b11d4d5381e2f3efb5f289da6 (patch) | |
tree | 8b6194fbebcc65b99079844fa9aa2b597c216f64 | |
parent | 778d03b59c62d21fd171b81c9fab3ba8496e319d (diff) |
replace remaining FlowFrmJoinLockGuard with SwFrmDeleteGuard
Given both tdf#91695 and the remaining crash on novell622972-2.html
it seems now safer to replace the remaining FlowFrmJoinLockGuard with
SwFrmDeleteGuard and rely on IsDeleteForbidden instead of IsJoinLocked
for the crashing layout edge-cases
and bundle the IsDeleteForbidden other IsDeleteForbidden users together
under SwFrmDeleteGuard
Change-Id: I017b6155daa3a6e49c5bee5b21ca4eddcfd5b5c0
-rw-r--r-- | sw/source/core/inc/flowfrm.hxx | 33 | ||||
-rw-r--r-- | sw/source/core/inc/frame.hxx | 26 | ||||
-rw-r--r-- | sw/source/core/layout/calcmove.cxx | 7 | ||||
-rw-r--r-- | sw/source/core/layout/flowfrm.cxx | 8 | ||||
-rw-r--r-- | sw/source/core/layout/fly.cxx | 12 | ||||
-rw-r--r-- | sw/source/core/layout/layact.cxx | 11 |
6 files changed, 43 insertions, 54 deletions
diff --git a/sw/source/core/inc/flowfrm.hxx b/sw/source/core/inc/flowfrm.hxx index 6421a9efc6bd..7c0e9b808dad 100644 --- a/sw/source/core/inc/flowfrm.hxx +++ b/sw/source/core/inc/flowfrm.hxx @@ -62,7 +62,6 @@ class SwFlowFrm friend inline void TableSplitRecalcUnlock( SwFlowFrm * ); // #i44049# friend class SwObjectFormatterTextFrm; - friend class FlowFrmJoinLockGuard; // TableSel is allowed to reset the follow-bit friend inline void UnsetFollow( SwFlowFrm *pFlow ); @@ -236,38 +235,6 @@ 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 FlowFrmJoinLockGuard -{ -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 - FlowFrmJoinLockGuard(SwLayoutFrm* pFrm) - { - m_pFlow = SwFlowFrm::CastFlowFrm(pFrm); - if (m_pFlow) - { - m_bOldJoinLocked = m_pFlow->IsJoinLocked(); - m_pFlow->LockJoin(); - } - else - { - m_bOldJoinLocked = false; - } - } - - ~FlowFrmJoinLockGuard() - { - if (m_pFlow && !m_bOldJoinLocked) - m_pFlow->UnlockJoin(); - } -}; - #endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/core/inc/frame.hxx b/sw/source/core/inc/frame.hxx index 714ba6ea4339..3e14805ec917 100644 --- a/sw/source/core/inc/frame.hxx +++ b/sw/source/core/inc/frame.hxx @@ -1150,6 +1150,32 @@ inline bool SwFrm::IsAccessibleFrm() const { return (GetType() & FRM_ACCESSIBLE) != 0; } + +//use this to protect a SwFrm for a given scope from getting deleted +class SwFrmDeleteGuard +{ +private: + SwFrm *m_pFrm; + bool m_bOldDeleteAllowed; +public: + //Flag pFrm for SwFrmDeleteGuard lifetime that we shouldn't delete + //it in e.g. SwSectionFrm::MergeNext etc because we will need it + //again after the SwFrmDeleteGuard dtor + SwFrmDeleteGuard(SwFrm* pFrm) + : m_pFrm(pFrm) + { + m_bOldDeleteAllowed = m_pFrm && !m_pFrm->IsDeleteForbidden(); + if (m_bOldDeleteAllowed) + m_pFrm->ForbidDelete(); + } + + ~SwFrmDeleteGuard() + { + if (m_bOldDeleteAllowed) + m_pFrm->AllowDelete(); + } +}; + #endif /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/core/layout/calcmove.cxx b/sw/source/core/layout/calcmove.cxx index 2e925327998e..0d9bbd2be6a1 100644 --- a/sw/source/core/layout/calcmove.cxx +++ b/sw/source/core/layout/calcmove.cxx @@ -346,9 +346,10 @@ void SwFrm::OptPrepareMake() if ( GetUpper() && !GetUpper()->IsFooterFrm() && !GetUpper()->IsFlyFrm() ) { - ForbidDelete(); - GetUpper()->Calc(getRootFrm()->GetCurrShell() ? getRootFrm()->GetCurrShell()->GetOut() : 0); - AllowDelete(); + { + SwFrmDeleteGuard aDeleteGuard(this); + GetUpper()->Calc(getRootFrm()->GetCurrShell() ? getRootFrm()->GetCurrShell()->GetOut() : 0); + } OSL_ENSURE( GetUpper(), ":-( Layout unstable (Upper gone)." ); if ( !GetUpper() ) return; diff --git a/sw/source/core/layout/flowfrm.cxx b/sw/source/core/layout/flowfrm.cxx index c78bc280a23a..2c009176fe3f 100644 --- a/sw/source/core/layout/flowfrm.cxx +++ b/sw/source/core/layout/flowfrm.cxx @@ -577,10 +577,10 @@ void SwFlowFrm::MoveSubTree( SwLayoutFrm* pParent, SwFrm* pSibling ) bool bInvaLay; { - //JoinLock pParent for the lifetime of the Cut/Paste call to avoid - //SwSectionFrm::MergeNext removing the pParent we're trying to reparent - //into - FlowFrmJoinLockGuard aJoinGuard(pParent); + //Ensure pParent persists for the lifetime of the Cut/Paste call to + //avoid SwSectionFrm::MergeNext removing the pParent we're trying to + //reparent into + SwFrmDeleteGuard aDeleteGuard(pParent); pOldParent = CutTree( &m_rThis ); bInvaLay = PasteTree( &m_rThis, pParent, pSibling, pOldParent ); } diff --git a/sw/source/core/layout/fly.cxx b/sw/source/core/layout/fly.cxx index ff51d377f405..877e618aa582 100644 --- a/sw/source/core/layout/fly.cxx +++ b/sw/source/core/layout/fly.cxx @@ -1463,14 +1463,10 @@ void CalcContent( SwLayoutFrm *pLay, if ( bNoCalcFollow && pFrm->IsTextFrm() ) static_cast<SwTextFrm*>(pFrm)->ForbidFollowFormat(); - const bool bDeleteForbidden(pSect && pSect->IsDeleteForbidden()); - if (pSect && !bDeleteForbidden) - pSect->ForbidDelete(); - - pFrm->Calc(pRenderContext); - - if (pSect && !bDeleteForbidden) - pSect->AllowDelete(); + { + SwFrmDeleteGuard aDeleteGuard(pSect); + pFrm->Calc(pRenderContext); + } // OD 14.03.2003 #i11760# - reset control flag for follow format. if ( pFrm->IsTextFrm() ) diff --git a/sw/source/core/layout/layact.cxx b/sw/source/core/layout/layact.cxx index 230769f7e8b5..8dfbcbcd3308 100644 --- a/sw/source/core/layout/layact.cxx +++ b/sw/source/core/layout/layact.cxx @@ -1223,11 +1223,10 @@ bool SwLayAction::FormatLayout( OutputDevice *pRenderContext, SwLayoutFrm *pLay, aOldRect = static_cast<SwPageFrm*>(pLay)->GetBoundRect(pRenderContext); } - bool const bDeleteForbidden(pLay->IsDeleteForbidden()); - pLay->ForbidDelete(); - pLay->Calc(pRenderContext); - if (!bDeleteForbidden) - pLay->AllowDelete(); + { + SwFrmDeleteGuard aDeleteGuard(pLay); + pLay->Calc(pRenderContext); + } if ( aOldFrame != pLay->Frm() ) bChanged = true; @@ -1375,7 +1374,7 @@ bool SwLayAction::FormatLayout( OutputDevice *pRenderContext, SwLayoutFrm *pLay, if ( pLay->IsFootnoteFrm() ) // no LayFrms as Lower return bChanged; - FlowFrmJoinLockGuard aJoinGuard(pLay); + SwFrmDeleteGuard aDeleteGuard(pLay); SwFrm *pLow = pLay->Lower(); bool bTabChanged = false; while ( pLow && pLow->GetUpper() == pLay ) |