diff options
author | Eike Rathke <erack@redhat.com> | 2012-01-31 20:40:47 +0100 |
---|---|---|
committer | Petr Mladek <pmladek@suse.cz> | 2012-02-01 10:23:39 +0100 |
commit | 6ccf504e590a47bb950aa179590f7e61146c043d (patch) | |
tree | 38f41a3edc2db7471846b54e49e9485bfec3eff7 | |
parent | don't delete thread while it is still running, fdo#45401 (diff) | |
download | core-6ccf504e590a47bb950aa179590f7e61146c043d.tar.gz core-6ccf504e590a47bb950aa179590f7e61146c043d.zip |
clone token in ScFormulaResult copy-ctor instead of referring
Replaces commit e2b11f4fd79dce4116badb0ecf6477546ca5d0d4
Prevent excessive references to single token instance during fill.
Because if not, we may run out of the 16-bit integer space to
store reference count.
Signed-off-by: Kohei Yoshida <kohei.yoshida@suse.com>
Signed-off-by: Markus Mohrhard <markus.mohrhard@googlemail.com>
Signed-off-by: Petr Mladek <pmladek@suse.cz>
-rw-r--r-- | sc/inc/formularesult.hxx | 23 |
1 files changed, 20 insertions, 3 deletions
diff --git a/sc/inc/formularesult.hxx b/sc/inc/formularesult.hxx index 2aa674c359f2..444552f835d1 100644 --- a/sc/inc/formularesult.hxx +++ b/sc/inc/formularesult.hxx @@ -41,6 +41,20 @@ class ScFormulaResult static const Multiline MULTILINE_FALSE = 1; static const Multiline MULTILINE_TRUE = 2; + // Clone token if the 16-bit only reference counter is nearing it's + // capacity during fill or copy&paste, leaving 4k for temporary passing + // around. (That should be enough for all times (TM) ;-) + static const sal_uInt16 MAX_TOKENREF_COUNT = 0xf000; + static void IncrementTokenRef( const formula::FormulaToken* & rp ) + { + if (rp) + { + if (rp->GetRef() >= MAX_TOKENREF_COUNT) + rp = rp->Clone(); + rp->IncRef(); + } + } + union { double mfValue; // double result direct for performance and memory consumption @@ -94,8 +108,12 @@ public: const ScMatrixFormulaCellToken* pMatFormula = r.GetMatrixFormulaCellToken(); if (pMatFormula) + { mpToken = new ScMatrixFormulaCellToken( *pMatFormula); - mpToken->IncRef(); + mpToken->IncRef(); + } + else + IncrementTokenRef( mpToken); } } else @@ -308,8 +326,7 @@ inline void ScFormulaResult::Assign( const ScFormulaResult & r ) inline void ScFormulaResult::SetToken( const formula::FormulaToken* p ) { ResetToDefaults(); - if (p) - p->IncRef(); + IncrementTokenRef( p); // Handle a result obtained from the interpreter to be assigned to a matrix // formula cell's ScMatrixFormulaCellToken. ScMatrixFormulaCellToken* pMatFormula = GetMatrixFormulaCellTokenNonConst(); |