[Libreoffice-commits] .: basic/qa basic/source

Noel Power noelp at kemper.freedesktop.org
Thu Jul 5 11:31:21 PDT 2012


 basic/qa/cppunit/test_nested_struct.cxx |   69 ++++++++++++++++++++++++++++++++
 basic/source/runtime/step0.cxx          |   63 +++++++++++++++--------------
 2 files changed, 102 insertions(+), 30 deletions(-)

New commits:
commit 0996c0d3193352fe65414ea5577f804dbad8d07b
Author: Noel Power <noel.power at novell.com>
Date:   Thu Jul 5 19:30:00 2012 +0100

    make unoCheckStruct uglier but detect unfixed type assignment + add new tests
    
    Change-Id: I6160e7d1abeeda1ea89e2fe15a9155041f2e5adb

diff --git a/basic/qa/cppunit/test_nested_struct.cxx b/basic/qa/cppunit/test_nested_struct.cxx
index defcaf1..21b4913 100644
--- a/basic/qa/cppunit/test_nested_struct.cxx
+++ b/basic/qa/cppunit/test_nested_struct.cxx
@@ -20,12 +20,16 @@ namespace
         Nested_Struct() {};
         void testAssign1();
         void testOldAssign();
+        void testUnfixedVarAssign();
+        void testFixedVarAssign();
         // Adds code needed to register the test suite
         CPPUNIT_TEST_SUITE(Nested_Struct);
 
         // Declares the method as a test to call
         CPPUNIT_TEST(testAssign1);
         CPPUNIT_TEST(testOldAssign);
+        CPPUNIT_TEST(testUnfixedVarAssign);
+        CPPUNIT_TEST(testFixedVarAssign);
 
         // End of test suite definition
         CPPUNIT_TEST_SUITE_END();
@@ -57,6 +61,35 @@ rtl::OUString sTestSource2(
 "End Function\n"
 );
 
+// it should be legal to assign a variant to a struct ( and copy by val )
+// make sure we aren't copying by reference, we make sure that l is not
+// a reference copy of b0.HorizontalLine, each one should have an
+// OuterLineWidth of 4 & 9 respectively and we should be returning
+// 13 the sum of the two ( hopefully unique values if we haven't copied by reference )
+rtl::OUString sTestSource3(
+    "Function testUnfixedVarAssign()\n"
+    "Dim b0 as new \"com.sun.star.table.TableBorder\"\n"
+    "l = b0.HorizontalLine\n"
+    "l.OuterLineWidth = 9\n"
+    "b0.HorizontalLine = l\n"
+    "l.OuterLineWidth = 4\n"
+    "testUnfixedVarAssign = b0.HorizontalLine.OuterLineWidth + l.OuterLineWidth\n"
+"End Function\n"
+);
+
+// nearly the same as above but this time for a fixed type
+// variable
+rtl::OUString sTestSource4(
+    "Function testFixedVarAssign()\n"
+    "Dim b0 as new \"com.sun.star.table.TableBorder\", l as new \"com.sun.star.table.BorderLine\"\n"
+    "l = b0.HorizontalLine\n"
+    "l.OuterLineWidth = 9\n"
+    "b0.HorizontalLine = l\n"
+    "l.OuterLineWidth = 4\n"
+    "testFixedVarAssign = b0.HorizontalLine.OuterLineWidth + l.OuterLineWidth\n"
+"End Function\n"
+);
+
 void Nested_Struct::testAssign1()
 {
     CPPUNIT_ASSERT_MESSAGE( "No resource manager", basicDLL().GetBasResMgr() != NULL );
@@ -93,6 +126,42 @@ void Nested_Struct::testOldAssign()
     CPPUNIT_ASSERT(pNew->GetInteger() == 9 );
 }
 
+void Nested_Struct::testUnfixedVarAssign()
+{
+    CPPUNIT_ASSERT_MESSAGE( "No resource manager", basicDLL().GetBasResMgr() != NULL );
+    StarBASICRef pBasic = new StarBASIC();
+    ResetError();
+    StarBASIC::SetGlobalErrorHdl( LINK( this, Nested_Struct, BasicErrorHdl ) );
+
+    SbModule* pMod = pBasic->MakeModule( rtl::OUString( "TestModule" ), sTestSource3 );
+    pMod->Compile();
+    CPPUNIT_ASSERT_MESSAGE("testUnfixedVarAssign fails with compile error",!HasError() );
+    SbMethod* pMeth = static_cast<SbMethod*>(pMod->Find( rtl::OUString("testUnfixedVarAssign"),  SbxCLASS_METHOD ));
+    CPPUNIT_ASSERT_MESSAGE("testUnfixedVarAssign no method found", pMeth );
+    SbxVariableRef refTemp = pMeth;
+    // forces a broadcast
+    SbxVariableRef pNew = new SbxMethod( *((SbxMethod*)pMeth));
+    CPPUNIT_ASSERT(pNew->GetInteger() == 13 );
+}
+
+void Nested_Struct::testFixedVarAssign()
+{
+    CPPUNIT_ASSERT_MESSAGE( "No resource manager", basicDLL().GetBasResMgr() != NULL );
+    StarBASICRef pBasic = new StarBASIC();
+    ResetError();
+    StarBASIC::SetGlobalErrorHdl( LINK( this, Nested_Struct, BasicErrorHdl ) );
+
+    SbModule* pMod = pBasic->MakeModule( rtl::OUString( "TestModule" ), sTestSource4 );
+    pMod->Compile();
+    CPPUNIT_ASSERT_MESSAGE("testFixedVarAssign fails with compile error",!HasError() );
+    SbMethod* pMeth = static_cast<SbMethod*>(pMod->Find( rtl::OUString("testFixedVarAssign"),  SbxCLASS_METHOD ));
+    CPPUNIT_ASSERT_MESSAGE("testFixedVarAssign no method found", pMeth );
+    SbxVariableRef refTemp = pMeth;
+    // forces a broadcast
+    SbxVariableRef pNew = new SbxMethod( *((SbxMethod*)pMeth));
+    CPPUNIT_ASSERT(pNew->GetInteger() == 13 );
+}
+
   // Put the test suite in the registry
   CPPUNIT_TEST_SUITE_REGISTRATION(Nested_Struct);
 } // namespace
diff --git a/basic/source/runtime/step0.cxx b/basic/source/runtime/step0.cxx
index 9149248..74b528a 100644
--- a/basic/source/runtime/step0.cxx
+++ b/basic/source/runtime/step0.cxx
@@ -335,54 +335,57 @@ void SbiRuntime::StepGET()
 inline bool checkUnoStructCopy( bool bVBA, SbxVariableRef& refVal, SbxVariableRef& refVar )
 {
     SbxDataType eVarType = refVar->GetType();
+    SbxDataType eValType = refVal->GetType();
 
-    if ( !( !bVBA|| ( bVBA && refVar->GetType() != SbxEMPTY ) ) )
+    if ( !( !bVBA|| ( bVBA && refVar->GetType() != SbxEMPTY ) ) || !refVar->CanWrite() )
         return false;
 
+    if ( eValType != SbxOBJECT )
+        return false;
+    // we seem to be duplicating parts of SbxValue=operator, maybe we should just move this to
+    // there :-/ not sure if for every '=' we would want struct handling
     if( eVarType != SbxOBJECT )
+    {
+        if ( refVar->IsFixed() )
+            return false;
+    }
+    // #115826: Exclude ProcedureProperties to avoid call to Property Get procedure
+    else if( refVar->ISA(SbProcedureProperty) )
         return false;
 
     SbxObjectRef xValObj = (SbxObject*)refVal->GetObject();
     if( !xValObj.Is() || xValObj->ISA(SbUnoAnyObject) )
         return false;
 
-    // #115826: Exclude ProcedureProperties to avoid call to Property Get procedure
-    if( refVar->ISA(SbProcedureProperty) )
-        return false;
-
-    SbxObjectRef xVarObj = (SbxObject*)refVar->GetObject();
-    SbxDataType eValType = refVal->GetType();
-    if( eValType == SbxOBJECT )
+    SbUnoObject* pUnoVal =  PTR_CAST(SbUnoObject,(SbxObject*)xValObj);
+    SbUnoStructRefObject* pUnoStructVal = PTR_CAST(SbUnoStructRefObject,(SbxObject*)xValObj);
+    Any aAny = pUnoVal ? pUnoVal->getUnoAny() : pUnoStructVal->getUnoAny();
+    if (  aAny.getValueType().getTypeClass() == TypeClass_STRUCT )
     {
+        refVar->SetType( SbxOBJECT );
+        SbxObjectRef xVarObj = (SbxObject*)refVar->GetObject();
         SbUnoObject* pUnoObj = PTR_CAST(SbUnoObject,(SbxObject*)xVarObj);
         SbUnoStructRefObject* pUnoStructObj = PTR_CAST(SbUnoStructRefObject,(SbxObject*)xVarObj);
 
-        SbUnoObject* pUnoVal =  PTR_CAST(SbUnoObject,(SbxObject*)xValObj);
-        SbUnoStructRefObject* pUnoStructVal = PTR_CAST(SbUnoStructRefObject,(SbxObject*)xValObj);
-
-        if ( ( !pUnoObj && !pUnoStructObj ) || ( !pUnoVal && !pUnoStructVal ) )
+        if ( ( !pUnoVal && !pUnoStructVal ) )
             return false;
-        Any aAny = pUnoVal ? pUnoVal->getUnoAny() : pUnoStructVal->getUnoAny();
 
-        if (  aAny.getValueType().getTypeClass() == TypeClass_STRUCT )
-        {
-            String sClassName = pUnoVal ? pUnoVal->GetClassName() : pUnoStructVal->GetClassName();
-            String sName = pUnoVal ? pUnoVal->GetName() : pUnoStructVal->GetName();
+        String sClassName = pUnoVal ? pUnoVal->GetClassName() : pUnoStructVal->GetClassName();
+        String sName = pUnoVal ? pUnoVal->GetName() : pUnoStructVal->GetName();
 
-            if ( pUnoObj )
-            {
-                SbUnoObject* pNewUnoObj = new SbUnoObject( sName, aAny );
-                // #70324: adopt ClassName
-                pNewUnoObj->SetClassName( sClassName );
-                refVar->PutObject( pNewUnoObj );
-                return true;
-            }
-            else
-            {
-                StructRefInfo aInfo = pUnoStructObj->getStructInfo();
-                aInfo.setValue( aAny );
-            }
+        if ( pUnoStructObj )
+        {
+            StructRefInfo aInfo = pUnoStructObj->getStructInfo();
+            aInfo.setValue( aAny );
+        }
+        else
+        {
+            SbUnoObject* pNewUnoObj = new SbUnoObject( sName, aAny );
+            // #70324: adopt ClassName
+            pNewUnoObj->SetClassName( sClassName );
+            refVar->PutObject( pNewUnoObj );
         }
+        return true;
     }
     return false;
 }


More information about the Libreoffice-commits mailing list