diff options
author | Eike Rathke <erack@erack.de> | 2011-08-23 23:50:08 +0200 |
---|---|---|
committer | Eike Rathke <erack@erack.de> | 2011-08-24 00:01:23 +0200 |
commit | de247b8805d3e60d2181ac6369b07f0a494cd1b6 (patch) | |
tree | 9eb440f0ab80054185597c815759cf407300c607 /sc | |
parent | 61aff182ab78af4cdd4e3d4d2b5e1b0872cb27f9 (diff) |
adapt to unused memory correctly
* ScColumn::DeleteRange() still failed in a case when cells of the very
last part of memory were removed that did not encompass the entire
range passed and nCount wasn't decremented as a result. Refactored
that loop over RemovedSegments.
Diffstat (limited to 'sc')
-rw-r--r-- | sc/source/core/data/column3.cxx | 48 |
1 files changed, 29 insertions, 19 deletions
diff --git a/sc/source/core/data/column3.cxx b/sc/source/core/data/column3.cxx index 384f98fa9d5b..8e8037a5914c 100644 --- a/sc/source/core/data/column3.cxx +++ b/sc/source/core/data/column3.cxx @@ -530,33 +530,43 @@ void ScColumn::DeleteRange( SCSIZE nStartIndex, SCSIZE nEndIndex, sal_uInt16 nDe { RemovedSegments_t::const_iterator aIt(aRemovedSegments.begin()); RemovedSegments_t::const_iterator aEnd(aRemovedSegments.end()); - if (aIt != aEnd) + // The indexes in aRemovedSegments denote cell positions in the + // original array. But as we are shifting it from the left, we have + // to compensate for already performed shifts for latter segments. + // TODO: use reverse iterators instead + SCSIZE nShift(0); + SCSIZE nStartSegment(nStartIndex); + bool bRemoved = false; + while (aIt != aEnd) { - SCSIZE nStartSegment(aIt->first); - bool bMoveSegment(aIt->second); - // The indexes in aRemovedSegments denote cell positions in the - // original array. But as we are shifting it from the left, we have - // to compensate for already performed shifts for latter segments. - // TODO: use reverse iterators instead - SCSIZE nShift(0); - ++aIt; - do - { - SCSIZE const nEndSegment(aIt->first); - if (bMoveSegment) - { + if (aIt->second) + { // this segment removed + if (!bRemoved) + nStartSegment = aIt->first; + // The first of removes in a row sets start (they should be + // alternating removed/notremoved anyway). + bRemoved = true; + } + else + { // this segment not removed + if (bRemoved) + { // previous segment(s) removed, move tail + SCSIZE const nEndSegment(aIt->first); memmove( &pItems[nStartSegment - nShift], &pItems[nEndSegment - nShift], (nCount - nEndSegment) * sizeof(ColEntry)); nShift += nEndSegment - nStartSegment; + bRemoved = false; } - nStartSegment = nEndSegment; - bMoveSegment = aIt->second; - ++aIt; - } while (aIt != aEnd); - nCount -= nShift; + } + ++aIt; } + // The last removed segment up to nCount is discarded, there's nothing + // following to be moved. + if (bRemoved) + nShift += nCount - nStartSegment; + nCount -= nShift; } // *** delete all formula cells *** |