LCOV - code coverage report
Current view: top level - cppuhelper/source - interfacecontainer.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 299 359 83.3 %
Date: 2012-08-25 Functions: 29 33 87.9 %
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: 270 515 52.4 %

           Branch data     Line data    Source code
       1                 :            : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2                 :            : /*************************************************************************
       3                 :            :  *
       4                 :            :  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       5                 :            :  *
       6                 :            :  * Copyright 2000, 2010 Oracle and/or its affiliates.
       7                 :            :  *
       8                 :            :  * OpenOffice.org - a multi-platform office productivity suite
       9                 :            :  *
      10                 :            :  * This file is part of OpenOffice.org.
      11                 :            :  *
      12                 :            :  * OpenOffice.org is free software: you can redistribute it and/or modify
      13                 :            :  * it under the terms of the GNU Lesser General Public License version 3
      14                 :            :  * only, as published by the Free Software Foundation.
      15                 :            :  *
      16                 :            :  * OpenOffice.org is distributed in the hope that it will be useful,
      17                 :            :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      18                 :            :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      19                 :            :  * GNU Lesser General Public License version 3 for more details
      20                 :            :  * (a copy is included in the LICENSE file that accompanied this code).
      21                 :            :  *
      22                 :            :  * You should have received a copy of the GNU Lesser General Public License
      23                 :            :  * version 3 along with OpenOffice.org.  If not, see
      24                 :            :  * <http://www.openoffice.org/license.html>
      25                 :            :  * for a copy of the LGPLv3 License.
      26                 :            :  *
      27                 :            :  ************************************************************************/
      28                 :            : 
      29                 :            : 
      30                 :            : #include <cppuhelper/interfacecontainer.hxx>
      31                 :            : #include <cppuhelper/queryinterface.hxx>
      32                 :            : #include <cppuhelper/propshlp.hxx>
      33                 :            : 
      34                 :            : #include <osl/diagnose.h>
      35                 :            : #include <osl/mutex.hxx>
      36                 :            : 
      37                 :            : #include <boost/unordered_map.hpp>
      38                 :            : 
      39                 :            : #include <com/sun/star/lang/XEventListener.hpp>
      40                 :            : 
      41                 :            : 
      42                 :            : using namespace osl;
      43                 :            : using namespace com::sun::star::uno;
      44                 :            : using namespace com::sun::star::lang;
      45                 :            : 
      46                 :            : namespace cppu
      47                 :            : {
      48                 :            : /**
      49                 :            :  * Reallocate the sequence.
      50                 :            :  */
      51                 :     662751 : static void realloc( Sequence< Reference< XInterface > > & rSeq, sal_Int32 nNewLen )
      52                 :            :     SAL_THROW(())
      53                 :            : {
      54                 :     662751 :     rSeq.realloc( nNewLen );
      55                 :     662751 : }
      56                 :            : 
      57                 :            : /**
      58                 :            :  * Remove an element from an interface sequence.
      59                 :            :  */
      60                 :     998034 : static void sequenceRemoveElementAt( Sequence< Reference< XInterface > > & rSeq, sal_Int32 index )
      61                 :            :     SAL_THROW(())
      62                 :            : {
      63                 :     998034 :     sal_Int32 nNewLen = rSeq.getLength() - 1;
      64                 :            : 
      65         [ +  - ]:     998034 :     Sequence< Reference< XInterface > > aDestSeq( rSeq.getLength() - 1 );
      66                 :            :     // getArray on a const sequence is faster
      67                 :     998034 :     const Reference< XInterface > * pSource = ((const Sequence< Reference< XInterface > > &)rSeq).getConstArray();
      68         [ +  - ]:     998034 :     Reference< XInterface > * pDest = aDestSeq.getArray();
      69                 :     998034 :     sal_Int32 i = 0;
      70         [ +  + ]:    3029399 :     for( ; i < index; i++ )
      71         [ +  - ]:    2031365 :         pDest[i] = pSource[i];
      72         [ +  + ]:    4047905 :     for( sal_Int32 j = i ; j < nNewLen; j++ )
      73         [ +  - ]:    3049871 :         pDest[j] = pSource[j+1];
      74 [ +  - ][ +  - ]:     998034 :     rSeq = aDestSeq;
      75                 :     998034 : }
      76                 :            : 
      77                 :            : #ifdef _MSC_VER
      78                 :            : #pragma warning( disable: 4786 )
      79                 :            : #endif
      80                 :            : 
      81                 :    1839068 : OInterfaceIteratorHelper::OInterfaceIteratorHelper( OInterfaceContainerHelper & rCont_ )
      82                 :            :     SAL_THROW(())
      83                 :    1839068 :     : rCont( rCont_ )
      84                 :            : {
      85         [ +  - ]:    1839067 :     MutexGuard aGuard( rCont.rMutex );
      86         [ +  + ]:    1839068 :     if( rCont.bInUse )
      87                 :            :         // worst case, two iterators at the same time
      88         [ +  - ]:        104 :         rCont.copyAndResetInUse();
      89                 :    1839068 :     bIsList = rCont_.bIsList;
      90                 :    1839068 :     aData = rCont_.aData;
      91         [ +  + ]:    1839068 :     if( bIsList )
      92                 :            :     {
      93                 :      90445 :         rCont.bInUse = sal_True;
      94                 :      90445 :         nRemain = aData.pAsSequence->getLength();
      95                 :            :     }
      96         [ +  + ]:    1748623 :     else if( aData.pAsInterface )
      97                 :            :     {
      98                 :     915486 :         aData.pAsInterface->acquire();
      99                 :     915486 :         nRemain = 1;
     100                 :            :     }
     101                 :            :     else
     102         [ +  - ]:    1839068 :         nRemain = 0;
     103                 :    1839068 : }
     104                 :            : 
     105                 :    1839068 : OInterfaceIteratorHelper::~OInterfaceIteratorHelper() SAL_THROW(())
     106                 :            : {
     107                 :            :     sal_Bool bShared;
     108                 :            :     {
     109         [ +  - ]:    1839068 :     MutexGuard aGuard( rCont.rMutex );
     110                 :            :     // bResetInUse protect the iterator against recursion
     111 [ +  + ][ +  + ]:    1839068 :     bShared = aData.pAsSequence == rCont.aData.pAsSequence && rCont.bIsList;
     112         [ +  + ]:    1839068 :     if( bShared )
     113                 :            :     {
     114                 :            :         OSL_ENSURE( rCont.bInUse, "OInterfaceContainerHelper must be in use" );
     115                 :      69234 :         rCont.bInUse = sal_False;
     116         [ +  - ]:    1839068 :     }
     117                 :            :     }
     118                 :            : 
     119         [ +  + ]:    1839068 :     if( !bShared )
     120                 :            :     {
     121         [ +  + ]:    1769834 :         if( bIsList )
     122                 :            :             // Sequence owned by the iterator
     123         [ +  - ]:      21211 :             delete aData.pAsSequence;
     124         [ +  + ]:    1748623 :         else if( aData.pAsInterface )
     125                 :            :             // Interface is acquired by the iterator
     126                 :     915486 :             aData.pAsInterface->release();
     127                 :            :     }
     128                 :    1839068 : }
     129                 :            : 
     130                 :    1298348 : XInterface * OInterfaceIteratorHelper::next() SAL_THROW(())
     131                 :            : {
     132         [ +  + ]:    1298348 :     if( nRemain )
     133                 :            :     {
     134                 :    1298347 :         nRemain--;
     135         [ +  + ]:    1298347 :         if( bIsList )
     136                 :            :             // typecase to const,so the getArray method is faster
     137                 :     382868 :             return aData.pAsSequence->getConstArray()[nRemain].get();
     138            [ + ]:     915479 :         else if( aData.pAsInterface )
     139                 :     915480 :             return aData.pAsInterface;
     140                 :            :     }
     141                 :            :     // exception
     142                 :    1298347 :     return 0;
     143                 :            : }
     144                 :            : 
     145                 :         19 : void OInterfaceIteratorHelper::remove() SAL_THROW(())
     146                 :            : {
     147         [ +  + ]:         19 :     if( bIsList )
     148                 :            :     {
     149                 :            :         OSL_ASSERT( nRemain >= 0 &&
     150                 :            :                     nRemain < aData.pAsSequence->getLength() );
     151         [ +  - ]:          2 :         XInterface * p = aData.pAsSequence->getConstArray()[nRemain].get();
     152         [ +  - ]:          2 :         rCont.removeInterface( * reinterpret_cast< const Reference< XInterface > * >( &p ) );
     153                 :            :     }
     154                 :            :     else
     155                 :            :     {
     156                 :            :         OSL_ASSERT( 0 == nRemain );
     157                 :         17 :         rCont.removeInterface( * reinterpret_cast< const Reference< XInterface > * >(&aData.pAsInterface));
     158                 :            :     }
     159                 :         19 : }
     160                 :            : 
     161                 :    1696895 : OInterfaceContainerHelper::OInterfaceContainerHelper( Mutex & rMutex_ ) SAL_THROW(())
     162                 :            :     : rMutex( rMutex_ )
     163                 :            :     , bInUse( sal_False )
     164                 :    1696895 :     , bIsList( sal_False )
     165                 :            : {
     166                 :    1696895 : }
     167                 :            : 
     168                 :    1633226 : OInterfaceContainerHelper::~OInterfaceContainerHelper() SAL_THROW(())
     169                 :            : {
     170                 :            :     OSL_ENSURE( !bInUse, "~OInterfaceContainerHelper but is in use" );
     171         [ +  + ]:    1633226 :     if( bIsList )
     172         [ +  - ]:         54 :         delete aData.pAsSequence;
     173         [ +  + ]:    1633172 :     else if( aData.pAsInterface )
     174                 :       9732 :         aData.pAsInterface->release();
     175                 :    1633226 : }
     176                 :            : 
     177                 :     359224 : sal_Int32 OInterfaceContainerHelper::getLength() const SAL_THROW(())
     178                 :            : {
     179         [ +  - ]:     359224 :     MutexGuard aGuard( rMutex );
     180         [ +  + ]:     359224 :     if( bIsList )
     181                 :      20994 :         return aData.pAsSequence->getLength();
     182         [ +  + ]:     338230 :     else if( aData.pAsInterface )
     183                 :      40291 :         return 1;
     184         [ +  - ]:     359224 :     return 0;
     185                 :            : }
     186                 :            : 
     187                 :       7494 : Sequence< Reference<XInterface> > OInterfaceContainerHelper::getElements() const SAL_THROW(())
     188                 :            : {
     189         [ +  - ]:       7494 :     MutexGuard aGuard( rMutex );
     190         [ +  + ]:       7494 :     if( bIsList )
     191         [ +  - ]:        729 :         return *aData.pAsSequence;
     192         [ +  + ]:       6765 :     else if( aData.pAsInterface )
     193                 :            :     {
     194         [ +  - ]:       6288 :         Reference<XInterface> x( aData.pAsInterface );
     195         [ +  - ]:       6288 :         return Sequence< Reference< XInterface > >( &x, 1 );
     196                 :            :     }
     197 [ +  - ][ +  - ]:       7494 :     return Sequence< Reference< XInterface > >();
     198                 :            : }
     199                 :            : 
     200                 :      11567 : void OInterfaceContainerHelper::copyAndResetInUse() SAL_THROW(())
     201                 :            : {
     202                 :            :     OSL_ENSURE( bInUse, "OInterfaceContainerHelper not in use" );
     203         [ +  - ]:      11567 :     if( bInUse )
     204                 :            :     {
     205                 :            :         // this should be the worst case. If a iterator is active
     206                 :            :         // and a new Listener is added.
     207         [ +  - ]:      11567 :         if( bIsList )
     208         [ +  - ]:      11567 :             aData.pAsSequence = new Sequence< Reference< XInterface > >( *aData.pAsSequence );
     209         [ #  # ]:          0 :         else if( aData.pAsInterface )
     210                 :          0 :             aData.pAsInterface->acquire();
     211                 :            : 
     212                 :      11567 :         bInUse = sal_False;
     213                 :            :     }
     214                 :      11567 : }
     215                 :            : 
     216                 :    2072986 : sal_Int32 OInterfaceContainerHelper::addInterface( const Reference<XInterface> & rListener ) SAL_THROW(())
     217                 :            : {
     218                 :            :     OSL_ASSERT( rListener.is() );
     219         [ +  - ]:    2072986 :     MutexGuard aGuard( rMutex );
     220         [ +  + ]:    2072986 :     if( bInUse )
     221         [ +  - ]:         68 :         copyAndResetInUse();
     222                 :            : 
     223         [ +  + ]:    2072986 :     if( bIsList )
     224                 :            :     {
     225                 :     662751 :         sal_Int32 nLen = aData.pAsSequence->getLength();
     226         [ +  - ]:     662751 :         realloc( *aData.pAsSequence, nLen +1 );
     227 [ +  - ][ +  - ]:     662751 :         aData.pAsSequence->getArray()[ nLen ] = rListener;
     228                 :     662751 :         return nLen +1;
     229                 :            :     }
     230         [ +  + ]:    1410235 :     else if( aData.pAsInterface )
     231                 :            :     {
     232         [ +  - ]:     362243 :         Sequence< Reference< XInterface > > * pSeq = new Sequence< Reference< XInterface > >( 2 );
     233         [ +  - ]:     362243 :         Reference<XInterface> * pArray = pSeq->getArray();
     234         [ +  - ]:     362243 :         pArray[0] = aData.pAsInterface;
     235         [ +  - ]:     362243 :         pArray[1] = rListener;
     236                 :     362243 :         aData.pAsInterface->release();
     237                 :     362243 :         aData.pAsSequence = pSeq;
     238                 :     362243 :         bIsList = sal_True;
     239                 :     362243 :         return 2;
     240                 :            :     }
     241                 :            :     else
     242                 :            :     {
     243         [ +  - ]:    1047992 :         aData.pAsInterface = rListener.get();
     244         [ +  - ]:    1047992 :         if( rListener.is() )
     245         [ +  - ]:    1047992 :             rListener->acquire();
     246                 :    1047992 :         return 1;
     247         [ +  - ]:    2072986 :     }
     248                 :            : }
     249                 :            : 
     250                 :    1967365 : sal_Int32 OInterfaceContainerHelper::removeInterface( const Reference<XInterface> & rListener ) SAL_THROW(())
     251                 :            : {
     252                 :            :     OSL_ASSERT( rListener.is() );
     253         [ +  - ]:    1967365 :     MutexGuard aGuard( rMutex );
     254         [ +  + ]:    1967365 :     if( bInUse )
     255         [ +  - ]:      11395 :         copyAndResetInUse();
     256                 :            : 
     257         [ +  + ]:    1967365 :     if( bIsList )
     258                 :            :     {
     259                 :    1002197 :         const Reference<XInterface> * pL = aData.pAsSequence->getConstArray();
     260                 :    1002197 :         sal_Int32 nLen = aData.pAsSequence->getLength();
     261                 :            :         sal_Int32 i;
     262         [ +  + ]:    3058590 :         for( i = 0; i < nLen; i++ )
     263                 :            :         {
     264                 :            :             // It is not valid to compare the Pointer direkt, but is is is much
     265                 :            :             // more faster.
     266 [ +  - ][ +  - ]:    3054425 :             if( pL[i].get() == rListener.get() )
                 [ +  + ]
     267                 :            :             {
     268         [ +  - ]:     998032 :                 sequenceRemoveElementAt( *aData.pAsSequence, i );
     269                 :     998032 :                 break;
     270                 :            :             }
     271                 :            :         }
     272                 :            : 
     273         [ +  + ]:    1002197 :         if( i == nLen )
     274                 :            :         {
     275                 :            :             // interface not found, use the correct compare method
     276         [ +  + ]:      29195 :             for( i = 0; i < nLen; i++ )
     277                 :            :             {
     278 [ +  - ][ +  + ]:      25030 :                 if( pL[i] == rListener )
     279                 :            :                 {
     280         [ +  - ]:          2 :                     sequenceRemoveElementAt(*aData.pAsSequence, i );
     281                 :          2 :                     break;
     282                 :            :                 }
     283                 :            :             }
     284                 :            :         }
     285                 :            : 
     286         [ +  + ]:    1002197 :         if( aData.pAsSequence->getLength() == 1 )
     287                 :            :         {
     288         [ +  - ]:     349872 :             XInterface * p = aData.pAsSequence->getConstArray()[0].get();
     289                 :     349872 :             p->acquire();
     290 [ +  - ][ +  - ]:     349872 :             delete aData.pAsSequence;
     291                 :     349872 :             aData.pAsInterface = p;
     292                 :     349872 :             bIsList = sal_False;
     293                 :     349872 :             return 1;
     294                 :            :         }
     295                 :            :         else
     296                 :     652325 :             return aData.pAsSequence->getLength();
     297                 :            :     }
     298 [ +  + ][ +  - ]:     965168 :     else if( aData.pAsInterface && Reference<XInterface>( aData.pAsInterface ) == rListener )
         [ +  - ][ +  + ]
                 [ +  + ]
           [ +  +  #  # ]
     299                 :            :     {
     300                 :     961879 :         aData.pAsInterface->release();
     301                 :     961879 :         aData.pAsInterface = 0;
     302                 :            :     }
     303 [ +  + ][ +  - ]:    1967365 :     return aData.pAsInterface ? 1 : 0;
     304                 :            : }
     305                 :            : 
     306                 :     711712 : void OInterfaceContainerHelper::disposeAndClear( const EventObject & rEvt ) SAL_THROW(())
     307                 :            : {
     308         [ +  - ]:     711712 :     ClearableMutexGuard aGuard( rMutex );
     309         [ +  - ]:     711712 :     OInterfaceIteratorHelper aIt( *this );
     310                 :            :     // Release container, in case new entries come while disposing
     311                 :            :     OSL_ENSURE( !bIsList || bInUse, "OInterfaceContainerHelper not in use" );
     312 [ +  + ][ +  + ]:     711712 :     if( !bIsList && aData.pAsInterface )
     313                 :      48367 :         aData.pAsInterface->release();
     314                 :            :     // set the member to null, use the iterator to delete the values
     315                 :     711712 :     aData.pAsInterface = NULL;
     316                 :     711712 :     bIsList = sal_False;
     317                 :     711712 :     bInUse = sal_False;
     318         [ +  - ]:     711712 :     aGuard.clear();
     319         [ +  + ]:     789108 :     while( aIt.hasMoreElements() )
     320                 :            :     {
     321                 :            :         try
     322                 :            :         {
     323 [ +  - ][ +  - ]:      77396 :             Reference<XEventListener > xLst( aIt.next(), UNO_QUERY );
     324         [ +  + ]:      77396 :             if( xLst.is() )
     325 [ +  - ][ +  + ]:      77396 :                 xLst->disposing( rEvt );
                 [ -  + ]
     326                 :            :         }
     327         [ +  - ]:       3676 :         catch ( RuntimeException & )
     328                 :            :         {
     329                 :            :             // be robust, if e.g. a remote bridge has disposed already.
     330                 :            :             // there is no way to delegate the error to the caller :o(.
     331                 :            :         }
     332 [ +  - ][ +  - ]:     711712 :     }
     333                 :     711712 : }
     334                 :            : 
     335                 :            : 
     336                 :         13 : void OInterfaceContainerHelper::clear() SAL_THROW(())
     337                 :            : {
     338         [ +  - ]:         13 :     ClearableMutexGuard aGuard( rMutex );
     339         [ +  - ]:         13 :     OInterfaceIteratorHelper aIt( *this );
     340                 :            :     // Release container, in case new entries come while disposing
     341                 :            :     OSL_ENSURE( !bIsList || bInUse, "OInterfaceContainerHelper not in use" );
     342 [ +  + ][ +  - ]:         13 :     if( !bIsList && aData.pAsInterface )
     343                 :          6 :         aData.pAsInterface->release();
     344                 :            :     // set the member to null, use the iterator to delete the values
     345                 :         13 :     aData.pAsInterface = 0;
     346                 :         13 :     bIsList = sal_False;
     347                 :         13 :     bInUse = sal_False;
     348                 :            :     // release mutex before aIt destructor call
     349 [ +  - ][ +  - ]:         13 :     aGuard.clear();
                 [ +  - ]
     350                 :         13 : }
     351                 :            : 
     352                 :            : // specialized class for type
     353                 :            : 
     354                 :            : typedef ::std::vector< std::pair < Type , void* > > t_type2ptr;
     355                 :            : 
     356                 :    1309459 : OMultiTypeInterfaceContainerHelper::OMultiTypeInterfaceContainerHelper( Mutex & rMutex_ )
     357                 :            :     SAL_THROW(())
     358                 :    1309459 :     : rMutex( rMutex_ )
     359                 :            : {
     360         [ +  - ]:    1309459 :     m_pMap = new t_type2ptr();
     361                 :    1309459 : }
     362                 :    1289369 : OMultiTypeInterfaceContainerHelper::~OMultiTypeInterfaceContainerHelper()
     363                 :            :     SAL_THROW(())
     364                 :            : {
     365                 :    1289369 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     366                 :    1289369 :     t_type2ptr::iterator iter = pMap->begin();
     367                 :    1289369 :     t_type2ptr::iterator end = pMap->end();
     368                 :            : 
     369 [ +  - ][ +  + ]:    1394201 :     while( iter != end )
     370                 :            :     {
     371 [ +  - ][ +  - ]:     104832 :         delete (OInterfaceContainerHelper*)(*iter).second;
     372                 :     104832 :         (*iter).second = 0;
     373                 :     104832 :         ++iter;
     374                 :            :     }
     375         [ +  - ]:    1289369 :     delete pMap;
     376                 :    1289369 : }
     377                 :          0 : Sequence< Type > OMultiTypeInterfaceContainerHelper::getContainedTypes() const
     378                 :            :     SAL_THROW(())
     379                 :            : {
     380                 :          0 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     381                 :            :     t_type2ptr::size_type nSize;
     382                 :            : 
     383         [ #  # ]:          0 :     ::osl::MutexGuard aGuard( rMutex );
     384                 :          0 :     nSize = pMap->size();
     385         [ #  # ]:          0 :     if( nSize )
     386                 :            :     {
     387         [ #  # ]:          0 :         ::com::sun::star::uno::Sequence< Type > aInterfaceTypes( nSize );
     388         [ #  # ]:          0 :         Type * pArray = aInterfaceTypes.getArray();
     389                 :            : 
     390                 :          0 :         t_type2ptr::iterator iter = pMap->begin();
     391                 :          0 :         t_type2ptr::iterator end = pMap->end();
     392                 :            : 
     393                 :          0 :         sal_Int32 i = 0;
     394 [ #  # ][ #  # ]:          0 :         while( iter != end )
     395                 :            :         {
     396                 :            :             // are interfaces added to this container?
     397 [ #  # ][ #  # ]:          0 :             if( ((OInterfaceContainerHelper*)(*iter).second)->getLength() )
     398                 :            :                 // yes, put the type in the array
     399                 :          0 :                 pArray[i++] = (*iter).first;
     400                 :          0 :             ++iter;
     401                 :            :         }
     402         [ #  # ]:          0 :         if( (t_type2ptr::size_type)i != nSize ) {
     403                 :            :             // may be empty container, reduce the sequence to the right size
     404 [ #  # ][ #  # ]:          0 :             aInterfaceTypes = ::com::sun::star::uno::Sequence< Type >( pArray, i );
                 [ #  # ]
     405                 :            :         }
     406 [ #  # ][ #  # ]:          0 :         return aInterfaceTypes;
     407                 :            :     }
     408 [ #  # ][ #  # ]:          0 :     return ::com::sun::star::uno::Sequence< Type >();
     409                 :            : }
     410                 :            : 
     411                 :    1314874 : static t_type2ptr::iterator findType(t_type2ptr *pMap, const Type & rKey )
     412                 :            : {
     413                 :    1314874 :     t_type2ptr::iterator iter = pMap->begin();
     414                 :    1314874 :     t_type2ptr::iterator end = pMap->end();
     415                 :            : 
     416 [ +  - ][ +  + ]:    2622634 :     while( iter != end )
     417                 :            :     {
     418         [ +  + ]:    1307760 :         if (iter->first == rKey)
     419                 :     716311 :             break;
     420                 :     591449 :         ++iter;
     421                 :            :     }
     422                 :    1314874 :     return iter;
     423                 :            : }
     424                 :            : 
     425                 :     796499 : OInterfaceContainerHelper * OMultiTypeInterfaceContainerHelper::getContainer( const Type & rKey ) const
     426                 :            :     SAL_THROW(())
     427                 :            : {
     428         [ +  - ]:     796499 :     ::osl::MutexGuard aGuard( rMutex );
     429                 :            : 
     430                 :     796499 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     431         [ +  - ]:     796499 :      t_type2ptr::iterator iter = findType( pMap, rKey );
     432 [ +  - ][ +  + ]:     796499 :     if( iter != pMap->end() )
     433                 :     314492 :             return (OInterfaceContainerHelper*) (*iter).second;
     434         [ +  - ]:     796499 :     return 0;
     435                 :            : }
     436                 :     293311 : sal_Int32 OMultiTypeInterfaceContainerHelper::addInterface(
     437                 :            :     const Type & rKey, const Reference< XInterface > & rListener )
     438                 :            :     SAL_THROW(())
     439                 :            : {
     440         [ +  - ]:     293311 :     ::osl::MutexGuard aGuard( rMutex );
     441                 :     293311 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     442         [ +  - ]:     293311 :     t_type2ptr::iterator iter = findType( pMap, rKey );
     443 [ +  - ][ +  + ]:     293311 :     if( iter == pMap->end() )
     444                 :            :     {
     445         [ +  - ]:     116556 :         OInterfaceContainerHelper * pLC = new OInterfaceContainerHelper( rMutex );
     446 [ +  - ][ +  - ]:     116556 :         pMap->push_back(std::pair<Type, void*>(rKey, pLC));
     447         [ +  - ]:     116556 :         return pLC->addInterface( rListener );
     448                 :            :     }
     449                 :            :     else
     450 [ +  - ][ +  - ]:     293311 :         return ((OInterfaceContainerHelper*)(*iter).second)->addInterface( rListener );
     451                 :            : }
     452                 :     225064 : sal_Int32 OMultiTypeInterfaceContainerHelper::removeInterface(
     453                 :            :     const Type & rKey, const Reference< XInterface > & rListener )
     454                 :            :     SAL_THROW(())
     455                 :            : {
     456         [ +  - ]:     225064 :     ::osl::MutexGuard aGuard( rMutex );
     457                 :            : 
     458                 :            :     // search container with id nUik
     459                 :     225064 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     460         [ +  - ]:     225064 :     t_type2ptr::iterator iter = findType( pMap, rKey );
     461                 :            :         // container found?
     462 [ +  - ][ +  - ]:     225064 :     if( iter != pMap->end() )
     463         [ +  - ]:     225064 :         return ((OInterfaceContainerHelper*)(*iter).second)->removeInterface( rListener );
     464                 :            : 
     465                 :            :     // no container with this id. Always return 0
     466         [ +  - ]:     225064 :     return 0;
     467                 :            : }
     468                 :    1101264 : void OMultiTypeInterfaceContainerHelper::disposeAndClear( const EventObject & rEvt )
     469                 :            :     SAL_THROW(())
     470                 :            : {
     471                 :    1101264 :     t_type2ptr::size_type nSize = 0;
     472                 :    1101264 :     OInterfaceContainerHelper ** ppListenerContainers = NULL;
     473                 :            :     {
     474         [ +  - ]:    1101264 :         ::osl::MutexGuard aGuard( rMutex );
     475                 :    1101264 :         t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     476                 :    1101264 :         nSize = pMap->size();
     477         [ +  + ]:    1101264 :         if( nSize )
     478                 :            :         {
     479                 :            :             typedef OInterfaceContainerHelper* ppp;
     480         [ +  - ]:      51458 :             ppListenerContainers = new ppp[nSize];
     481                 :            :             //ppListenerContainers = new (ListenerContainer*)[nSize];
     482                 :            : 
     483                 :      51458 :             t_type2ptr::iterator iter = pMap->begin();
     484                 :      51458 :             t_type2ptr::iterator end = pMap->end();
     485                 :            : 
     486                 :      51458 :             t_type2ptr::size_type i = 0;
     487 [ +  - ][ +  + ]:     130117 :             while( iter != end )
     488                 :            :             {
     489                 :      78659 :                 ppListenerContainers[i++] = (OInterfaceContainerHelper*)(*iter).second;
     490                 :      78659 :                 ++iter;
     491                 :            :             }
     492         [ +  - ]:    1101264 :         }
     493                 :            :     }
     494                 :            : 
     495                 :            :     // create a copy, because do not fire event in a guarded section
     496         [ +  + ]:    1179923 :     for( t_type2ptr::size_type i = 0;
     497                 :            :             i < nSize; i++ )
     498                 :            :     {
     499         [ +  - ]:      78659 :         if( ppListenerContainers[i] )
     500                 :      78659 :             ppListenerContainers[i]->disposeAndClear( rEvt );
     501                 :            :     }
     502                 :            : 
     503         [ +  + ]:    1101264 :     delete [] ppListenerContainers;
     504                 :    1101264 : }
     505                 :          0 : void OMultiTypeInterfaceContainerHelper::clear()
     506                 :            :     SAL_THROW(())
     507                 :            : {
     508         [ #  # ]:          0 :     ::osl::MutexGuard aGuard( rMutex );
     509                 :          0 :     t_type2ptr * pMap = (t_type2ptr *)m_pMap;
     510                 :          0 :     t_type2ptr::iterator iter = pMap->begin();
     511                 :          0 :     t_type2ptr::iterator end = pMap->end();
     512                 :            : 
     513 [ #  # ][ #  # ]:          0 :     while( iter != end )
     514                 :            :     {
     515         [ #  # ]:          0 :         ((OInterfaceContainerHelper*)(*iter).second)->clear();
     516                 :          0 :         ++iter;
     517         [ #  # ]:          0 :     }
     518                 :          0 : }
     519                 :            : 
     520                 :            : // specialized class for long
     521                 :            : 
     522                 :            : typedef ::std::vector< std::pair < sal_Int32 , void* > > t_long2ptr;
     523                 :            : 
     524                 :      49301 : static t_long2ptr::iterator findLong(t_long2ptr *pMap, sal_Int32 nKey )
     525                 :            : {
     526                 :      49301 :     t_long2ptr::iterator iter = pMap->begin();
     527                 :      49301 :     t_long2ptr::iterator end = pMap->end();
     528                 :            : 
     529 [ +  - ][ +  + ]:     239616 :     while( iter != end )
     530                 :            :     {
     531 [ +  - ][ +  + ]:     190315 :         if (iter->first == nKey)
     532                 :      19849 :             break;
     533         [ +  - ]:     170466 :         ++iter;
     534                 :            :     }
     535                 :      49301 :     return iter;
     536                 :            : }
     537                 :            : 
     538                 :     238075 : OMultiTypeInterfaceContainerHelperInt32::OMultiTypeInterfaceContainerHelperInt32( Mutex & rMutex_ )
     539                 :            :     SAL_THROW(())
     540                 :            :     : m_pMap( NULL )
     541                 :     238075 :     , rMutex( rMutex_ )
     542                 :            : {
     543                 :            :     // delay pMap allocation until necessary.
     544                 :     238075 : }
     545                 :     234445 : OMultiTypeInterfaceContainerHelperInt32::~OMultiTypeInterfaceContainerHelperInt32()
     546                 :            :     SAL_THROW(())
     547                 :            : {
     548         [ +  + ]:     234445 :     if (!m_pMap)
     549                 :            :         return;
     550                 :            : 
     551                 :       2491 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     552                 :       2491 :     t_long2ptr::iterator iter = pMap->begin();
     553                 :       2491 :     t_long2ptr::iterator end = pMap->end();
     554                 :            : 
     555 [ +  - ][ +  + ]:      11943 :     while( iter != end )
     556                 :            :     {
     557 [ +  - ][ +  - ]:       9452 :         delete (OInterfaceContainerHelper*)(*iter).second;
                 [ +  - ]
     558         [ +  - ]:       9452 :         (*iter).second = 0;
     559         [ +  - ]:       9452 :         ++iter;
     560                 :            :     }
     561         [ +  - ]:     234445 :     delete pMap;
     562                 :     234445 : }
     563                 :          0 : Sequence< sal_Int32 > OMultiTypeInterfaceContainerHelperInt32::getContainedTypes() const
     564                 :            :     SAL_THROW(())
     565                 :            : {
     566                 :          0 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     567                 :            :     t_long2ptr::size_type nSize;
     568                 :            : 
     569         [ #  # ]:          0 :     ::osl::MutexGuard aGuard( rMutex );
     570         [ #  # ]:          0 :     nSize = pMap ? pMap->size() : 0;
     571         [ #  # ]:          0 :     if( nSize )
     572                 :            :     {
     573         [ #  # ]:          0 :         ::com::sun::star::uno::Sequence< sal_Int32 > aInterfaceTypes( nSize );
     574         [ #  # ]:          0 :         sal_Int32 * pArray = aInterfaceTypes.getArray();
     575                 :            : 
     576                 :          0 :         t_long2ptr::iterator iter = pMap->begin();
     577                 :          0 :         t_long2ptr::iterator end = pMap->end();
     578                 :            : 
     579                 :          0 :         sal_Int32 i = 0;
     580 [ #  # ][ #  # ]:          0 :         while( iter != end )
     581                 :            :         {
     582                 :            :             // are interfaces added to this container?
     583 [ #  # ][ #  # ]:          0 :             if( ((OInterfaceContainerHelper*)(*iter).second)->getLength() )
                 [ #  # ]
     584                 :            :                 // yes, put the type in the array
     585         [ #  # ]:          0 :                 pArray[i++] = (*iter).first;
     586         [ #  # ]:          0 :             ++iter;
     587                 :            :         }
     588         [ #  # ]:          0 :         if( (t_long2ptr::size_type)i != nSize ) {
     589                 :            :             // may be empty container, reduce the sequence to the right size
     590 [ #  # ][ #  # ]:          0 :             aInterfaceTypes = ::com::sun::star::uno::Sequence< sal_Int32 >( pArray, i );
                 [ #  # ]
     591                 :            :         }
     592 [ #  # ][ #  # ]:          0 :         return aInterfaceTypes;
     593                 :            :     }
     594 [ #  # ][ #  # ]:          0 :     return ::com::sun::star::uno::Sequence< sal_Int32 >();
     595                 :            : }
     596                 :      56404 : OInterfaceContainerHelper * OMultiTypeInterfaceContainerHelperInt32::getContainer( const sal_Int32 & rKey ) const
     597                 :            :     SAL_THROW(())
     598                 :            : {
     599         [ +  - ]:      56404 :     ::osl::MutexGuard aGuard( rMutex );
     600                 :            : 
     601         [ +  + ]:      56404 :     if (!m_pMap)
     602                 :      31139 :         return 0;
     603                 :      25265 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     604         [ +  - ]:      25265 :      t_long2ptr::iterator iter = findLong( pMap, rKey );
     605 [ +  - ][ +  + ]:      25265 :     if( iter != pMap->end() )
     606         [ +  - ]:       5566 :             return (OInterfaceContainerHelper*) (*iter).second;
     607         [ +  - ]:      56404 :     return 0;
     608                 :            : }
     609                 :      14893 : sal_Int32 OMultiTypeInterfaceContainerHelperInt32::addInterface(
     610                 :            :     const sal_Int32 & rKey, const Reference< XInterface > & rListener )
     611                 :            :     SAL_THROW(())
     612                 :            : {
     613         [ +  - ]:      14893 :     ::osl::MutexGuard aGuard( rMutex );
     614         [ +  + ]:      14893 :     if (!m_pMap)
     615 [ +  - ][ +  - ]:       2632 :         m_pMap = new t_long2ptr();
     616                 :      14893 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     617         [ +  - ]:      14893 :     t_long2ptr::iterator iter = findLong( pMap, rKey );
     618 [ +  - ][ +  + ]:      14893 :      if( iter == pMap->end() )
     619                 :            :     {
     620         [ +  - ]:       9751 :         OInterfaceContainerHelper * pLC = new OInterfaceContainerHelper( rMutex );
     621 [ +  - ][ +  - ]:       9751 :         pMap->push_back(std::pair< sal_Int32, void* >(rKey, pLC));
     622         [ +  - ]:       9751 :         return pLC->addInterface( rListener );
     623                 :            :     }
     624                 :            :     else
     625 [ +  - ][ +  - ]:      14893 :         return ((OInterfaceContainerHelper*)(*iter).second)->addInterface( rListener );
                 [ +  - ]
     626                 :            : }
     627                 :       9143 : sal_Int32 OMultiTypeInterfaceContainerHelperInt32::removeInterface(
     628                 :            :     const sal_Int32 & rKey, const Reference< XInterface > & rListener )
     629                 :            :     SAL_THROW(())
     630                 :            : {
     631         [ +  - ]:       9143 :     ::osl::MutexGuard aGuard( rMutex );
     632                 :            : 
     633         [ -  + ]:       9143 :     if (!m_pMap)
     634                 :          0 :         return 0;
     635                 :            :     // search container with id nUik
     636                 :       9143 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     637         [ +  - ]:       9143 :     t_long2ptr::iterator iter = findLong( pMap, rKey );
     638                 :            :         // container found?
     639 [ +  - ][ +  + ]:       9143 :     if( iter != pMap->end() )
     640 [ +  - ][ +  - ]:       9141 :         return ((OInterfaceContainerHelper*)(*iter).second)->removeInterface( rListener );
     641                 :            : 
     642                 :            :     // no container with this id. Always return 0
     643         [ +  - ]:       9143 :     return 0;
     644                 :            : }
     645                 :      20996 : void OMultiTypeInterfaceContainerHelperInt32::disposeAndClear( const EventObject & rEvt )
     646                 :            :     SAL_THROW(())
     647                 :            : {
     648                 :      20996 :     t_long2ptr::size_type nSize = 0;
     649                 :      20996 :     OInterfaceContainerHelper ** ppListenerContainers = NULL;
     650                 :            :     {
     651         [ +  - ]:      20996 :         ::osl::MutexGuard aGuard( rMutex );
     652         [ +  + ]:      20996 :         if (!m_pMap)
     653                 :      20996 :             return;
     654                 :            : 
     655                 :       2380 :         t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     656                 :       2380 :         nSize = pMap->size();
     657         [ +  - ]:       2380 :         if( nSize )
     658                 :            :         {
     659                 :            :             typedef OInterfaceContainerHelper* ppp;
     660         [ +  - ]:       2380 :             ppListenerContainers = new ppp[nSize];
     661                 :            : 
     662                 :       2380 :             t_long2ptr::iterator iter = pMap->begin();
     663                 :       2380 :             t_long2ptr::iterator end = pMap->end();
     664                 :            : 
     665                 :       2380 :             t_long2ptr::size_type i = 0;
     666 [ +  - ][ +  + ]:      10961 :             while( iter != end )
     667                 :            :             {
     668         [ +  - ]:       8581 :                 ppListenerContainers[i++] = (OInterfaceContainerHelper*)(*iter).second;
     669         [ +  - ]:       8581 :                 ++iter;
     670                 :            :             }
     671 [ +  - ][ +  + ]:      20996 :         }
     672                 :            :     }
     673                 :            : 
     674                 :            :     // create a copy, because do not fire event in a guarded section
     675         [ +  + ]:      29577 :     for( t_long2ptr::size_type i = 0;
     676                 :            :             i < nSize; i++ )
     677                 :            :     {
     678         [ +  - ]:       8581 :         if( ppListenerContainers[i] )
     679                 :       8581 :             ppListenerContainers[i]->disposeAndClear( rEvt );
     680                 :            :     }
     681                 :            : 
     682         [ +  - ]:       2380 :     delete [] ppListenerContainers;
     683                 :            : }
     684                 :          0 : void OMultiTypeInterfaceContainerHelperInt32::clear()
     685                 :            :     SAL_THROW(())
     686                 :            : {
     687         [ #  # ]:          0 :     ::osl::MutexGuard aGuard( rMutex );
     688         [ #  # ]:          0 :     if (!m_pMap)
     689                 :          0 :         return;
     690                 :          0 :     t_long2ptr * pMap = (t_long2ptr *)m_pMap;
     691                 :          0 :     t_long2ptr::iterator iter = pMap->begin();
     692                 :          0 :     t_long2ptr::iterator end = pMap->end();
     693                 :            : 
     694 [ #  # ][ #  # ]:          0 :     while( iter != end )
     695                 :            :     {
     696 [ #  # ][ #  # ]:          0 :         ((OInterfaceContainerHelper*)(*iter).second)->clear();
     697         [ #  # ]:          0 :         ++iter;
     698 [ #  # ][ #  # ]:          0 :     }
     699                 :            : }
     700                 :            : 
     701                 :            : }
     702                 :            : 
     703                 :            : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10