sc/inc/address.hxx | 24 +++- sc/qa/unit/ucalc_formula.cxx | 184 ++++++++++++++++++++++++++++++++++++ sc/source/core/data/column.cxx | 6 - sc/source/core/data/conditio.cxx | 6 - sc/source/core/data/documen7.cxx | 6 - sc/source/core/data/drwlayer.cxx | 6 - sc/source/core/data/formulacell.cxx | 6 - sc/source/core/tool/address.cxx | 47 +++++++-- sc/source/core/tool/refdata.cxx | 9 + sc/source/core/tool/token.cxx | 66 ++++++++++-- sc/source/filter/html/htmlimp.cxx | 6 - sc/source/filter/html/htmlpars.cxx | 13 ++ sc/source/ui/docshell/docfunc.cxx | 18 ++- sc/source/ui/view/gridwin.cxx | 12 +- 14 files changed, 365 insertions(+), 44 deletions(-)
New commits: commit fe445df126ff0be771494dfef3aec09ca82f8aef Author: Eike Rathke <er...@redhat.com> Date: Fri Dec 11 14:42:35 2015 +0100 unit test for sticky end col/row anchors, tdf#92779 Change-Id: I78584e37e5944327db9cc5b6472a9e7ea972b37e diff --git a/sc/qa/unit/ucalc_formula.cxx b/sc/qa/unit/ucalc_formula.cxx index 841ae60..c42df7d 100644 --- a/sc/qa/unit/ucalc_formula.cxx +++ b/sc/qa/unit/ucalc_formula.cxx @@ -1545,6 +1545,190 @@ void Test::testFormulaRefUpdateRange() if (!checkFormula(*m_pDoc, ScAddress(0,2,0), "SUM($C$6:$F$9)")) CPPUNIT_FAIL("Wrong formula in A3."); + m_pDoc->InsertTab(1, "StickyRange"); + + // A3:A18 all possible combinations of relative and absolute addressing, + // leaving one row above and below unreferenced. + ScAddress aPos(0,2,1); + m_pDoc->SetString( aPos, "=B2:B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B2:B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B2:$B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B2:$B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B$2:B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B$2:B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B$2:$B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=B$2:$B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B2:B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B2:B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B2:$B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B2:$B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B$2:B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B$2:B$1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B$2:$B1048575"); + aPos.IncRow(); + m_pDoc->SetString( aPos, "=$B$2:$B$1048575"); + aPos.IncRow(); + // A19 reference to two cells on one row. + m_pDoc->SetString( aPos, "=B1048575:C1048575"); + aPos.IncRow(); + + // Insert 2 rows in the middle to shift bottom reference down and make it + // sticky. + m_pDoc->InsertRow( ScRange( aPos, ScAddress(MAXCOL,aPos.Row()+1,1))); + + // A3:A18 must not result in #REF! anywhere. + bool bCheck = true; + aPos.Set(0,2,1); + bCheck &= checkFormula(*m_pDoc, aPos, "B2:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B2:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B2:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B2:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$2:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$2:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$2:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$2:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B2:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B2:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B2:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B2:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$2:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$2:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$2:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$2:$B$1048576"); + aPos.IncRow(); + if (!bCheck) + CPPUNIT_FAIL("Wrong reference in A3:A18 after insertion."); + + // A19 reference to one row shifted out should be #REF! + bCheck &= checkFormula(*m_pDoc, aPos, "B#REF!:C#REF!"); + if (!bCheck) + CPPUNIT_FAIL("Wrong reference in A19 after insertion."); + // A19 enter reference to last row. + m_pDoc->SetString( aPos, "=B1048576:C1048576"); + aPos.IncRow(); + + // Delete row 1 to shift top reference up, bottom reference stays sticky. + m_pDoc->DeleteRow(ScRange(0,0,1,MAXCOL,0,1)); + + // Check sticky bottom references and display of entire column references, + // now in A2:A17. + bCheck = true; + aPos.Set(0,1,1); + bCheck &= checkFormula(*m_pDoc, aPos, "B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B1:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B1:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$1:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$1:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B1:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B1:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$1:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$1:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:$B"); + aPos.IncRow(); + if (!bCheck) + CPPUNIT_FAIL("Wrong reference in A2:A17 after deletion."); + + // A18 reference to one last row should be shifted up. + bCheck &= checkFormula(*m_pDoc, aPos, "B1048575:C1048575"); + if (!bCheck) + CPPUNIT_FAIL("Wrong reference in A18 after deletion."); + aPos.IncRow(); + + // Insert 4 rows in the middle. + m_pDoc->InsertRow( ScRange( aPos, ScAddress(MAXCOL,aPos.Row()+3,1))); + // Delete 2 rows in the middle. + m_pDoc->DeleteRow( ScRange( aPos, ScAddress(MAXCOL,aPos.Row()+1,1))); + + // References in A2:A17 must still be the same. + bCheck = true; + aPos.Set(0,1,1); + bCheck &= checkFormula(*m_pDoc, aPos, "B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B1:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B1:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$1:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B$1:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B1:B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:$B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B1:$B$1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$1:B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:B"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B$1:$B1048576"); + aPos.IncRow(); + bCheck &= checkFormula(*m_pDoc, aPos, "$B:$B"); + aPos.IncRow(); + if (!bCheck) + CPPUNIT_FAIL("Wrong reference in A2:A17 after deletion."); + + m_pDoc->DeleteTab(1); + m_pDoc->DeleteTab(0); } commit 9c1ba0988f5db05bb796eaf7cf902a0b601c6736 Author: Eike Rathke <er...@redhat.com> Date: Fri Dec 11 14:27:33 2015 +0100 geez, how about actually checking the Move() error return? tdf#92779 related Handle failure condition where we know how to treat it, i.e. when updating references, assert in all other places that so far silently ignored it and implicitly assumed the failing Move() truncating at bounds would be alright. In case we'll encounter an assertion we'll have to inspect those places and decide what to do about it. Noticed this error with a reference like B1048575 and inserting two rows above, it became B1048576 instead of B#REF! Change-Id: I00757f3ed2e305b591178047933ed60f1533317e diff --git a/sc/inc/address.hxx b/sc/inc/address.hxx index 4bf5ee5..34d49fb 100644 --- a/sc/inc/address.hxx +++ b/sc/inc/address.hxx @@ -305,9 +305,15 @@ public: const ScDocument* pDocument = nullptr, const Details& rDetails = detailsOOOa1) const; - // The document for the maximum defined sheet number - SC_DLLPUBLIC bool Move( SCsCOL nDeltaX, SCsROW nDeltaY, SCsTAB nDeltaZ, - ScDocument* pDocument = nullptr ); + /** + @param rErrorPos + If FALSE is returned, the positions contain <0 or >MAX... + values if shifted out of bounds. + @param pDocument + The document for the maximum defined sheet number. + */ + SC_DLLPUBLIC SAL_WARN_UNUSED_RESULT bool Move( SCsCOL nDeltaX, SCsROW nDeltaY, SCsTAB nDeltaZ, + ScAddress& rErrorPos, ScDocument* pDocument = nullptr ); inline bool operator==( const ScAddress& rAddress ) const; inline bool operator!=( const ScAddress& rAddress ) const; @@ -535,8 +541,16 @@ public: inline void GetVars( SCCOL& nCol1, SCROW& nRow1, SCTAB& nTab1, SCCOL& nCol2, SCROW& nRow2, SCTAB& nTab2 ) const; SC_DLLPUBLIC void PutInOrder(); - // The document for the maximum defined sheet number - SC_DLLPUBLIC bool Move( SCsCOL aDeltaX, SCsROW aDeltaY, SCsTAB aDeltaZ, ScDocument* pDocument = nullptr ); + + /** + @param rErrorRange + If FALSE is returned, the positions contain <0 or >MAX... + values if shifted out of bounds. + @param pDocument + The document for the maximum defined sheet number. + */ + SC_DLLPUBLIC SAL_WARN_UNUSED_RESULT bool Move( SCsCOL aDeltaX, SCsROW aDeltaY, SCsTAB aDeltaZ, + ScRange& rErrorRange, ScDocument* pDocument = nullptr ); SC_DLLPUBLIC void ExtendTo( const ScRange& rRange ); SC_DLLPUBLIC bool Intersects( const ScRange& rRange ) const; // do two ranges intersect? diff --git a/sc/source/core/data/column.cxx b/sc/source/core/data/column.cxx index d820abc..c09f096 100644 --- a/sc/source/core/data/column.cxx +++ b/sc/source/core/data/column.cxx @@ -2066,11 +2066,15 @@ class UpdateRefOnNonCopy : std::unary_function<sc::FormulaGroupEntry, void> if (pTop->UpdatePosOnShift(*mpCxt)) { + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); // Update the positions of all formula cells. for (++pp; pp != ppEnd; ++pp) // skip the top cell. { ScFormulaCell* pFC = *pp; - pFC->aPos.Move(mpCxt->mnColDelta, mpCxt->mnRowDelta, mpCxt->mnTabDelta); + if (!pFC->aPos.Move(mpCxt->mnColDelta, mpCxt->mnRowDelta, mpCxt->mnTabDelta, aErrorPos)) + { + assert(!"can't move formula cell"); + } } if (pCode->IsRecalcModeOnRefMove()) diff --git a/sc/source/core/data/conditio.cxx b/sc/source/core/data/conditio.cxx index abcd231..6dd4c32 100644 --- a/sc/source/core/data/conditio.cxx +++ b/sc/source/core/data/conditio.cxx @@ -510,7 +510,11 @@ void ScConditionEntry::UpdateReference( sc::RefUpdateContext& rCxt ) bool bChangedPos = false; if (rCxt.meMode == URM_INSDEL && rCxt.maRange.In(aSrcPos)) { - aSrcPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aSrcPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + { + assert(!"can't move ScConditionEntry"); + } bChangedPos = aSrcPos != aOldSrcPos; } diff --git a/sc/source/core/data/documen7.cxx b/sc/source/core/data/documen7.cxx index 447a688..cfa3d2f 100644 --- a/sc/source/core/data/documen7.cxx +++ b/sc/source/core/data/documen7.cxx @@ -246,11 +246,15 @@ void ScDocument::BroadcastRefMoved( const sc::RefMovedHint& rHint ) // Re-start area listeners on the new range. { + ScRange aErrorRange( ScAddress::UNINITIALIZED ); std::vector<sc::AreaListener>::iterator it = aAreaListeners.begin(), itEnd = aAreaListeners.end(); for (; it != itEnd; ++it) { ScRange aNewRange = it->maArea; - aNewRange.Move(rDelta.Col(), rDelta.Row(), rDelta.Tab()); + if (!aNewRange.Move(rDelta.Col(), rDelta.Row(), rDelta.Tab(), aErrorRange)) + { + assert(!"can't move AreaListener"); + } pBASM->StartListeningArea(aNewRange, it->mbGroupListening, it->mpListener); } } diff --git a/sc/source/core/data/drwlayer.cxx b/sc/source/core/data/drwlayer.cxx index 6d48458..dbf1fe7 100644 --- a/sc/source/core/data/drwlayer.cxx +++ b/sc/source/core/data/drwlayer.cxx @@ -1425,6 +1425,7 @@ static bool lcl_MoveRanges( ::std::vector< ScRangeList >& rRangesVector, const S { bool bChanged = false; + ScRange aErrorRange( ScAddress::UNINITIALIZED ); ::std::vector< ScRangeList >::iterator aIt = rRangesVector.begin(); for( ;aIt!=rRangesVector.end(); ++aIt ) { @@ -1437,7 +1438,10 @@ static bool lcl_MoveRanges( ::std::vector< ScRangeList >& rRangesVector, const S SCsCOL nDiffX = rDestPos.Col() - (SCsCOL)rSourceRange.aStart.Col(); SCsROW nDiffY = rDestPos.Row() - (SCsROW)rSourceRange.aStart.Row(); SCsTAB nDiffZ = rDestPos.Tab() - (SCsTAB)rSourceRange.aStart.Tab(); - pRange->Move( nDiffX, nDiffY, nDiffZ ); + if (!pRange->Move( nDiffX, nDiffY, nDiffZ, aErrorRange)) + { + assert(!"can't move range"); + } bChanged = true; } } diff --git a/sc/source/core/data/formulacell.cxx b/sc/source/core/data/formulacell.cxx index 0c5edae..5c87b52 100644 --- a/sc/source/core/data/formulacell.cxx +++ b/sc/source/core/data/formulacell.cxx @@ -2899,7 +2899,11 @@ bool ScFormulaCell::UpdatePosOnShift( const sc::RefUpdateContext& rCxt ) // This formula cell itself is being shifted during cell range // insertion or deletion. Update its position. - aPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + { + assert(!"can't move ScFormulaCell"); + } return true; } diff --git a/sc/source/core/tool/address.cxx b/sc/source/core/tool/address.cxx index a48baa5..e060f0a 100644 --- a/sc/source/core/tool/address.cxx +++ b/sc/source/core/tool/address.cxx @@ -2100,30 +2100,53 @@ OUString ScRange::Format( sal_uInt16 nFlags, const ScDocument* pDoc, return r.makeStringAndClear(); } -bool ScAddress::Move( SCsCOL dx, SCsROW dy, SCsTAB dz, ScDocument* pDoc ) +bool ScAddress::Move( SCsCOL dx, SCsROW dy, SCsTAB dz, ScAddress& rErrorPos, ScDocument* pDoc ) { SCsTAB nMaxTab = pDoc ? pDoc->GetTableCount() : MAXTAB; dx = Col() + dx; dy = Row() + dy; dz = Tab() + dz; bool bValid = true; + rErrorPos.SetCol(dx); if( dx < 0 ) - dx = 0, bValid = false; + { + dx = 0; + bValid = false; + } else if( dx > MAXCOL ) - dx = MAXCOL, bValid =false; + { + dx = MAXCOL; + bValid =false; + } + rErrorPos.SetRow(dy); if( dy < 0 ) - dy = 0, bValid = false; + { + dy = 0; + bValid = false; + } else if( dy > MAXROW ) - dy = MAXROW, bValid =false; + { + dy = MAXROW; + bValid =false; + } + rErrorPos.SetTab(dz); if( dz < 0 ) - dz = 0, bValid = false; + { + dz = 0; + bValid = false; + } else if( dz > nMaxTab ) - dz = nMaxTab, bValid =false; + { + // Always set MAXTAB+1 so further checks without ScDocument detect invalid. + rErrorPos.SetTab(MAXTAB+1); + dz = nMaxTab; + bValid =false; + } Set( dx, dy, dz ); return bValid; } -bool ScRange::Move( SCsCOL dx, SCsROW dy, SCsTAB dz, ScDocument* pDoc ) +bool ScRange::Move( SCsCOL dx, SCsROW dy, SCsTAB dz, ScRange& rErrorRange, ScDocument* pDoc ) { bool bColRange = (aStart.Col() < aEnd.Col()); bool bRowRange = (aStart.Row() < aEnd.Row()); @@ -2131,18 +2154,22 @@ bool ScRange::Move( SCsCOL dx, SCsROW dy, SCsTAB dz, ScDocument* pDoc ) dy = 0; // Entire column not to be moved. if (dx && aStart.Col() == 0 && aEnd.Col() == MAXCOL) dx = 0; // Entire row not to be moved. - bool b1 = aStart.Move( dx, dy, dz, pDoc ); + bool b1 = aStart.Move( dx, dy, dz, rErrorRange.aStart, pDoc ); if (dx && bColRange && aEnd.Col() == MAXCOL) dx = 0; // End column sticky. if (dy && bRowRange && aEnd.Row() == MAXROW) dy = 0; // End row sticky. SCTAB nOldTab = aEnd.Tab(); - bool b2 = aEnd.Move( dx, dy, dz, pDoc ); + bool b2 = aEnd.Move( dx, dy, dz, rErrorRange.aEnd, pDoc ); if (!b2) { // End column or row of a range may have become sticky. bColRange = (!dx || (bColRange && aEnd.Col() == MAXCOL)); + if (dx && bColRange) + rErrorRange.aEnd.SetCol(MAXCOL); bRowRange = (!dy || (bRowRange && aEnd.Row() == MAXROW)); + if (dy && bRowRange) + rErrorRange.aEnd.SetRow(MAXROW); b2 = bColRange && bRowRange && (aEnd.Tab() - nOldTab == dz); } return b1 && b2; diff --git a/sc/source/core/tool/refdata.cxx b/sc/source/core/tool/refdata.cxx index d977802..53bf2e4 100644 --- a/sc/source/core/tool/refdata.cxx +++ b/sc/source/core/tool/refdata.cxx @@ -211,15 +211,24 @@ void ScSingleRefData::SetAddress( const ScAddress& rAddr, const ScAddress& rPos else mnCol = rAddr.Col(); + if (!ValidCol(rAddr.Col())) + SetColDeleted(true); + if (Flags.bRowRel) mnRow = rAddr.Row() - rPos.Row(); else mnRow = rAddr.Row(); + if (!ValidRow(rAddr.Row())) + SetRowDeleted(true); + if (Flags.bTabRel) mnTab = rAddr.Tab() - rPos.Tab(); else mnTab = rAddr.Tab(); + + if (!ValidTab( rAddr.Tab(), MAXTAB)) + SetTabDeleted(true); } SCROW ScSingleRefData::Row() const diff --git a/sc/source/core/tool/token.cxx b/sc/source/core/tool/token.cxx index 49bbe2e..29274ae 100644 --- a/sc/source/core/tool/token.cxx +++ b/sc/source/core/tool/token.cxx @@ -2861,7 +2861,13 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnShift( const sc::RefUpdateCon ScAddress aNewPos = rOldPos; bool bCellShifted = rCxt.maRange.In(rOldPos); if (bCellShifted) - aNewPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + { + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aNewPos.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + { + assert(!"can't move"); + } + } TokenPointers aPtrs( pCode, nLen, pRPN, nRPN); for (size_t j=0; j<2; ++j) @@ -2903,7 +2909,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnShift( const sc::RefUpdateCon if (rCxt.maRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + aAbs = aErrorPos; aRes.mbReferenceModified = true; } @@ -2960,7 +2968,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnShift( const sc::RefUpdateCon if (rCxt.maRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorRange)) + aAbs = aErrorRange; aRes.mbReferenceModified = true; } else if (rCxt.maRange.Intersects(aAbs)) @@ -3031,7 +3041,11 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnMove( // When moving, the range is the destination range. We need to use the old // range prior to the move for hit analysis. ScRange aOldRange = rCxt.maRange; - aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta); + ScRange aErrorMoveRange( ScAddress::UNINITIALIZED ); + if (!aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta, aErrorMoveRange)) + { + assert(!"can't move"); + } bool b3DFlag = rOldPos.Tab() != rNewPos.Tab() || rCxt.mnTabDelta; @@ -3054,7 +3068,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnMove( ScAddress aAbs = rRef.toAbs(rOldPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + aAbs = aErrorPos; aRes.mbReferenceModified = true; } @@ -3069,7 +3085,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceOnMove( ScRange aAbs = rRef.toAbs(rOldPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorRange)) + aAbs = aErrorRange; aRes.mbReferenceModified = true; } @@ -3112,7 +3130,11 @@ sc::RefUpdateResult ScTokenArray::MoveReference( const ScAddress& rPos, const sc sc::RefUpdateResult aRes; ScRange aOldRange = rCxt.maRange; - aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta); + ScRange aErrorMoveRange( ScAddress::UNINITIALIZED ); + if (!aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta, aErrorMoveRange)) + { + assert(!"can't move"); + } FormulaToken** p = pCode; FormulaToken** pEnd = p + static_cast<size_t>(nLen); @@ -3127,7 +3149,9 @@ sc::RefUpdateResult ScTokenArray::MoveReference( const ScAddress& rPos, const sc ScAddress aAbs = rRef.toAbs(rPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + aAbs = aErrorPos; rRef.SetAddress(aAbs, rPos); if (rCxt.mnTabDelta) rRef.SetFlag3D(aAbs.Tab()!=rPos.Tab()); @@ -3141,7 +3165,9 @@ sc::RefUpdateResult ScTokenArray::MoveReference( const ScAddress& rPos, const sc ScRange aAbs = rRef.toAbs(rPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorRange)) + aAbs = aErrorRange; rRef.SetRange(aAbs, rPos); if (rCxt.mnTabDelta) rRef.Ref1.SetFlag3D(aAbs.aStart.Tab()!=rPos.Tab()); @@ -3562,7 +3588,11 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceInMovedName( const sc::RefUpdat { // When moving, the range is the destination range. ScRange aOldRange = rCxt.maRange; - aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta); + ScRange aErrorMoveRange( ScAddress::UNINITIALIZED ); + if (!aOldRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta, aErrorMoveRange)) + { + assert(!"can't move"); + } // In a named expression, we'll move the reference only when the reference // is entirely absolute. @@ -3591,7 +3621,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceInMovedName( const sc::RefUpdat ScAddress aAbs = rRef.toAbs(rPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorPos)) + aAbs = aErrorPos; aRes.mbReferenceModified = true; } @@ -3608,7 +3640,9 @@ sc::RefUpdateResult ScTokenArray::AdjustReferenceInMovedName( const sc::RefUpdat ScRange aAbs = rRef.toAbs(rPos); if (aOldRange.In(aAbs)) { - aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aAbs.Move(rCxt.mnColDelta, rCxt.mnRowDelta, rCxt.mnTabDelta, aErrorRange)) + aAbs = aErrorRange; aRes.mbReferenceModified = true; } @@ -4141,8 +4175,14 @@ void checkBounds( ScRange aCheckRange = rCxt.maRange; if (rCxt.meMode == URM_MOVE) + { // Check bounds against the old range prior to the move. - aCheckRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aCheckRange.Move(-rCxt.mnColDelta, -rCxt.mnRowDelta, -rCxt.mnTabDelta, aErrorRange)) + { + assert(!"can't move"); + } + } checkBounds(rPos, nGroupLen, aCheckRange, rRef, rBounds); } diff --git a/sc/source/filter/html/htmlimp.cxx b/sc/source/filter/html/htmlimp.cxx index 8e82e30..2be6faa 100644 --- a/sc/source/filter/html/htmlimp.cxx +++ b/sc/source/filter/html/htmlimp.cxx @@ -178,10 +178,14 @@ void ScHTMLImport::WriteToDocument( ScHTMLTable* pTable = nullptr; ScHTMLTableId nTableId = SC_HTML_GLOBAL_TABLE; + ScRange aErrorRange( ScAddress::UNINITIALIZED ); while( (pTable = pGlobTable->FindNestedTable( ++nTableId )) != nullptr ) { pTable->GetDocRange( aNewRange ); - aNewRange.Move( nColDiff, nRowDiff, nTabDiff ); + if (!aNewRange.Move( nColDiff, nRowDiff, nTabDiff, aErrorRange )) + { + assert(!"can't move"); + } // insert table number as name InsertRangeName( mpDoc, ScfTools::GetNameFromHTMLIndex( nTableId ), aNewRange ); // insert table id as name diff --git a/sc/source/filter/html/htmlpars.cxx b/sc/source/filter/html/htmlpars.cxx index 8e906bd..5ecfeaa 100644 --- a/sc/source/filter/html/htmlpars.cxx +++ b/sc/source/filter/html/htmlpars.cxx @@ -2296,7 +2296,12 @@ ScHTMLPos ScHTMLTable::GetDocPos( const ScHTMLPos& rCellPos ) const void ScHTMLTable::GetDocRange( ScRange& rRange ) const { rRange.aStart = rRange.aEnd = maDocBasePos.MakeAddr(); - rRange.aEnd.Move( static_cast< SCsCOL >( GetDocSize( tdCol ) ) - 1, static_cast< SCsROW >( GetDocSize( tdRow ) ) - 1, 0 ); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!rRange.aEnd.Move( static_cast< SCsCOL >( GetDocSize( tdCol ) ) - 1, + static_cast< SCsROW >( GetDocSize( tdRow ) ) - 1, 0, aErrorPos)) + { + assert(!"can't move"); + } } void ScHTMLTable::ApplyCellBorders( ScDocument* pDoc, const ScAddress& rFirstPos ) const @@ -2479,7 +2484,11 @@ void ScHTMLTable::InsertNewCell( const ScHTMLSize& rSpanSize ) // insert the new range into the cell lists ScRange aNewRange( maCurrCell.MakeAddr() ); - aNewRange.aEnd.Move( rSpanSize.mnCols - 1, rSpanSize.mnRows - 1, 0 ); + ScAddress aErrorPos( ScAddress::UNINITIALIZED ); + if (!aNewRange.aEnd.Move( rSpanSize.mnCols - 1, rSpanSize.mnRows - 1, 0, aErrorPos)) + { + assert(!"can't move"); + } if( rSpanSize.mnRows > 1 ) { maVMergedCells.Append( aNewRange ); diff --git a/sc/source/ui/docshell/docfunc.cxx b/sc/source/ui/docshell/docfunc.cxx index 4b4afc13..41d23f5 100644 --- a/sc/source/ui/docshell/docfunc.cxx +++ b/sc/source/ui/docshell/docfunc.cxx @@ -1635,11 +1635,21 @@ bool ScDocFunc::InsertCells( const ScRange& rRange, const ScMarkData* pTabMark, // If insertion is for full cols/rows and after the current // selection, then shift the range accordingly - if ( eCmd == INS_INSROWS_AFTER ) { - aTargetRange.Move(0, rRange.aEnd.Row() - rRange.aStart.Row() + 1, 0); + if ( eCmd == INS_INSROWS_AFTER ) + { + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aTargetRange.Move(0, rRange.aEnd.Row() - rRange.aStart.Row() + 1, 0, aErrorRange)) + { + assert(!"can't move"); + } } - if ( eCmd == INS_INSCOLS_AFTER ) { - aTargetRange.Move(rRange.aEnd.Col() - rRange.aStart.Col() + 1, 0, 0); + if ( eCmd == INS_INSCOLS_AFTER ) + { + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + if (!aTargetRange.Move(rRange.aEnd.Col() - rRange.aStart.Col() + 1, 0, 0, aErrorRange)) + { + assert(!"can't move"); + } } SCCOL nStartCol = aTargetRange.aStart.Col(); diff --git a/sc/source/ui/view/gridwin.cxx b/sc/source/ui/view/gridwin.cxx index 344f71fe..de0d32e 100644 --- a/sc/source/ui/view/gridwin.cxx +++ b/sc/source/ui/view/gridwin.cxx @@ -4254,13 +4254,15 @@ sal_Int8 ScGridWindow::DropTransferObj( ScTransferObj* pTransObj, SCCOL nDestPos if ( meDragInsertMode == INS_CELLSDOWN && nDestPosX == aSource.aStart.Col() && nDestPosY < aSource.aStart.Row() ) { - bDone = aSource.Move( 0, nSizeY, 0, pSourceDoc ); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + bDone = aSource.Move( 0, nSizeY, 0, aErrorRange, pSourceDoc ); nCorrectCursorPosRow = nSizeY; } else if ( meDragInsertMode == INS_CELLSRIGHT && nDestPosY == aSource.aStart.Row() && nDestPosX < aSource.aStart.Col() ) { - bDone = aSource.Move( nSizeX, 0, 0, pSourceDoc ); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + bDone = aSource.Move( nSizeX, 0, 0, aErrorRange, pSourceDoc ); nCorrectCursorPosCol = nSizeX; } } @@ -4304,11 +4306,13 @@ sal_Int8 ScGridWindow::DropTransferObj( ScTransferObj* pTransObj, SCCOL nDestPos { if ( eCmd == DEL_CELLSUP && nDestPosY > aSource.aEnd.Row() ) { - bDone = aDest.Move( 0, -nSizeY, 0, pThisDoc ); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + bDone = aDest.Move( 0, -nSizeY, 0, aErrorRange, pThisDoc ); } else if ( eCmd == DEL_CELLSLEFT && nDestPosX > aSource.aEnd.Col() ) { - bDone = aDest.Move( -nSizeX, 0, 0, pThisDoc ); + ScRange aErrorRange( ScAddress::UNINITIALIZED ); + bDone = aDest.Move( -nSizeX, 0, 0, aErrorRange, pThisDoc ); } pDocSh->UpdateOle( pViewData ); pView->CellContentChanged(); _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits