sc/inc/cell.hxx                |    2 --
 sc/inc/formularesult.hxx       |   35 ++++++++++++++++++++---------------
 sc/source/core/data/cell.cxx   |    5 -----
 sc/source/core/data/table4.cxx |    1 -
 4 files changed, 20 insertions(+), 23 deletions(-)

New commits:
commit 742b36ed8bd3880d4dcf6022fbc3165a213d80bb
Author: Eike Rathke <er...@redhat.com>
Date:   Tue Jan 31 20:40:47 2012 +0100

    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.

diff --git a/sc/inc/formularesult.hxx b/sc/inc/formularesult.hxx
index c1cb906..8a35b43 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();
commit 78997434dd813e7a8d949e510a9de8bbf77b8025
Author: Eike Rathke <er...@redhat.com>
Date:   Tue Jan 31 20:40:10 2012 +0100

    Revert "Prevent excessive references to single token instance during fill."
    
    This reverts commit e2b11f4fd79dce4116badb0ecf6477546ca5d0d4.
    
    To be replaced with a different solution.

diff --git a/sc/inc/cell.hxx b/sc/inc/cell.hxx
index 3bc7aee..52244f6 100644
--- a/sc/inc/cell.hxx
+++ b/sc/inc/cell.hxx
@@ -535,8 +535,6 @@ public:
     bool            IsMultilineResult();
 
     void            MaybeInterpret();
-
-    void            ResetFormulaResult();
 };
 
 //          Iterator for references in a formula cell
diff --git a/sc/inc/formularesult.hxx b/sc/inc/formularesult.hxx
index 94c62f8..c1cb906 100644
--- a/sc/inc/formularesult.hxx
+++ b/sc/inc/formularesult.hxx
@@ -117,8 +117,6 @@ public:
                                         mpToken->DecRef();
                                 }
 
-    inline void Reset();
-
     /** Well, guess what ... */
     inline  ScFormulaResult &   operator=( const ScFormulaResult & r );
 
@@ -218,16 +216,6 @@ public:
     inline ScMatrixFormulaCellToken* GetMatrixFormulaCellTokenNonConst();
 };
 
-inline void ScFormulaResult::Reset()
-{
-    ResetToDefaults();
-
-    if (mbToken && mpToken)
-        mpToken->DecRef();
-
-    mbToken = true;
-    mpToken = NULL;
-}
 
 inline void ScFormulaResult::ResetToDefaults()
 {
diff --git a/sc/source/core/data/cell.cxx b/sc/source/core/data/cell.cxx
index 1f89aed..2f3df26 100644
--- a/sc/source/core/data/cell.cxx
+++ b/sc/source/core/data/cell.cxx
@@ -2041,11 +2041,6 @@ void ScFormulaCell::MaybeInterpret()
         Interpret();
 }
 
-void ScFormulaCell::ResetFormulaResult()
-{
-    aResult.Reset();
-}
-
 EditTextObject* ScFormulaCell::CreateURLObject()
 {
     String aCellText;
diff --git a/sc/source/core/data/table4.cxx b/sc/source/core/data/table4.cxx
index 6a21a07..dac4111 100644
--- a/sc/source/core/data/table4.cxx
+++ b/sc/source/core/data/table4.cxx
@@ -429,7 +429,6 @@ void ScTable::FillFormula(sal_uLong& /* nFormulaCounter */, 
bool /* bFirst */, S
     pDocument->SetNoListening( true );  // noch falsche Referenzen
     ScAddress aAddr( nDestCol, nDestRow, nTab );
     ScFormulaCell* pDestCell = new ScFormulaCell( *pSrcCell, *pDocument, aAddr 
);
-    pDestCell->ResetFormulaResult(); // formula cell is interpreted later 
during fill.
     aCol[nDestCol].Insert(nDestRow, pDestCell);
 
     if ( bLast && pDestCell->GetMatrixFlag() )
_______________________________________________
Libreoffice-commits mailing list
Libreoffice-commits@lists.freedesktop.org
http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits

Reply via email to