LCOV - code coverage report
Current view: top level - pyuno/source/module - pyuno_runtime.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 273 472 57.8 %
Date: 2012-08-25 Functions: 19 23 82.6 %
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: 327 955 34.2 %

           Branch data     Line data    Source code
       1                 :            : /* -*- Mode: C++; eval:(c-set-style "bsd"); tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2                 :            : /*
       3                 :            :  * This file is part of the LibreOffice project.
       4                 :            :  *
       5                 :            :  * This Source Code Form is subject to the terms of the Mozilla Public
       6                 :            :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7                 :            :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8                 :            :  *
       9                 :            :  * This file incorporates work covered by the following license notice:
      10                 :            :  *
      11                 :            :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12                 :            :  *   contributor license agreements. See the NOTICE file distributed
      13                 :            :  *   with this work for additional information regarding copyright
      14                 :            :  *   ownership. The ASF licenses this file to you under the Apache
      15                 :            :  *   License, Version 2.0 (the "License"); you may not use this file
      16                 :            :  *   except in compliance with the License. You may obtain a copy of
      17                 :            :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18                 :            :  */
      19                 :            : 
      20                 :            : #include "pyuno_impl.hxx"
      21                 :            : 
      22                 :            : #include <osl/thread.h>
      23                 :            : #include <osl/module.h>
      24                 :            : #include <osl/process.h>
      25                 :            : #include <rtl/strbuf.hxx>
      26                 :            : #include <rtl/ustrbuf.hxx>
      27                 :            : #include <rtl/bootstrap.hxx>
      28                 :            : #include <locale.h>
      29                 :            : 
      30                 :            : #include <typelib/typedescription.hxx>
      31                 :            : 
      32                 :            : #include <com/sun/star/beans/XMaterialHolder.hpp>
      33                 :            : 
      34                 :            : using rtl::OUString;
      35                 :            : using rtl::OUStringToOString;
      36                 :            : using rtl::OUStringBuffer;
      37                 :            : using rtl::OStringBuffer;
      38                 :            : using rtl::OString;
      39                 :            : 
      40                 :            : using com::sun::star::uno::Reference;
      41                 :            : using com::sun::star::uno::XInterface;
      42                 :            : using com::sun::star::uno::Any;
      43                 :            : using com::sun::star::uno::TypeDescription;
      44                 :            : using com::sun::star::uno::Sequence;
      45                 :            : using com::sun::star::uno::Type;
      46                 :            : using com::sun::star::uno::UNO_QUERY;
      47                 :            : using com::sun::star::uno::Exception;
      48                 :            : using com::sun::star::uno::RuntimeException;
      49                 :            : using com::sun::star::uno::XComponentContext;
      50                 :            : using com::sun::star::lang::XSingleServiceFactory;
      51                 :            : using com::sun::star::lang::XUnoTunnel;
      52                 :            : using com::sun::star::reflection::XIdlReflection;
      53                 :            : using com::sun::star::script::XTypeConverter;
      54                 :            : using com::sun::star::script::XInvocationAdapterFactory2;
      55                 :            : using com::sun::star::script::XInvocation;
      56                 :            : using com::sun::star::beans::XMaterialHolder;
      57                 :            : using com::sun::star::beans::XIntrospection;
      58                 :            : 
      59                 :            : #include <vector>
      60                 :            : 
      61                 :            : namespace pyuno
      62                 :            : {
      63                 :            : #define USTR_ASCII(x) OUString(  x  )
      64                 :            : 
      65                 :            : static PyTypeObject RuntimeImpl_Type =
      66                 :            : {
      67                 :            :     PyVarObject_HEAD_INIT (&PyType_Type, 0)
      68                 :            :     "pyuno_runtime",
      69                 :            :     sizeof (RuntimeImpl),
      70                 :            :     0,
      71                 :            :     (destructor) RuntimeImpl::del,
      72                 :            :     (printfunc) 0,
      73                 :            :     (getattrfunc) 0,
      74                 :            :     (setattrfunc) 0,
      75                 :            :     0,
      76                 :            :     (reprfunc) 0,
      77                 :            :     0,
      78                 :            :     0,
      79                 :            :     0,
      80                 :            :     (hashfunc) 0,
      81                 :            :     (ternaryfunc) 0,
      82                 :            :     (reprfunc) 0,
      83                 :            :     (getattrofunc)0,
      84                 :            :     (setattrofunc)0,
      85                 :            :     NULL,
      86                 :            :     0,
      87                 :            :     NULL,
      88                 :            :     (traverseproc)0,
      89                 :            :     (inquiry)0,
      90                 :            :     (richcmpfunc)0,
      91                 :            :     0,
      92                 :            :     (getiterfunc)0,
      93                 :            :     (iternextfunc)0,
      94                 :            :     NULL,
      95                 :            :     NULL,
      96                 :            :     NULL,
      97                 :            :     NULL,
      98                 :            :     NULL,
      99                 :            :     (descrgetfunc)0,
     100                 :            :     (descrsetfunc)0,
     101                 :            :     0,
     102                 :            :     (initproc)0,
     103                 :            :     (allocfunc)0,
     104                 :            :     (newfunc)0,
     105                 :            :     (freefunc)0,
     106                 :            :     (inquiry)0,
     107                 :            :     NULL,
     108                 :            :     NULL,
     109                 :            :     NULL,
     110                 :            :     NULL,
     111                 :            :     NULL,
     112                 :            :     (destructor)0
     113                 :            : #if PY_VERSION_HEX >= 0x02060000
     114                 :            :     , 0
     115                 :            : #endif
     116                 :            : };
     117                 :            : 
     118                 :            : /*----------------------------------------------------------------------
     119                 :            :   Runtime implementation
     120                 :            :  -----------------------------------------------------------------------*/
     121                 :     172817 : static void getRuntimeImpl( PyRef & globalDict, PyRef &runtimeImpl )
     122                 :            :     throw ( com::sun::star::uno::RuntimeException )
     123                 :            : {
     124                 :     172817 :     PyThreadState * state = PyThreadState_Get();
     125         [ -  + ]:     172817 :     if( ! state )
     126                 :            :     {
     127                 :            :         throw RuntimeException( OUString( "python global interpreter must be held (thread must be attached)" ),
     128         [ #  # ]:          0 :                                 Reference< XInterface > () );
     129                 :            :     }
     130                 :            : 
     131         [ +  - ]:     172817 :     globalDict = PyRef( PyModule_GetDict(PyImport_AddModule("__main__")));
     132                 :            : 
     133         [ -  + ]:     172817 :     if( ! globalDict.is() ) // FATAL !
     134                 :            :     {
     135         [ #  # ]:          0 :         throw RuntimeException( OUString( "can't find __main__ module" ), Reference< XInterface > ());
     136                 :            :     }
     137         [ +  - ]:     172817 :     runtimeImpl = PyDict_GetItemString( globalDict.get() , "pyuno_runtime" );
     138                 :     172817 : }
     139                 :            : 
     140                 :        112 : static PyRef importUnoModule( ) throw ( RuntimeException )
     141                 :            : {
     142                 :            :     // import the uno module
     143         [ +  - ]:        112 :     PyRef module( PyImport_ImportModule( "uno" ), SAL_NO_ACQUIRE );
     144 [ -  + ][ +  - ]:        112 :     if( PyErr_Occurred() )
     145                 :            :     {
     146                 :          0 :         PyRef excType, excValue, excTraceback;
     147         [ #  # ]:          0 :         PyErr_Fetch( (PyObject **)&excType, (PyObject**)&excValue,(PyObject**)&excTraceback);
     148                 :            :         // As of Python 2.7 this gives a rather non-useful "<traceback object at 0xADDRESS>",
     149                 :            :         // but it is the best we can do in the absence of uno._uno_extract_printable_stacktrace
     150                 :            :         // Who knows, a future Python might print something better.
     151         [ #  # ]:          0 :         PyRef str( PyObject_Str( excTraceback.get() ), SAL_NO_ACQUIRE );
     152                 :            : 
     153                 :          0 :         OUStringBuffer buf;
     154         [ #  # ]:          0 :         buf.appendAscii( "python object raised an unknown exception (" );
     155         [ #  # ]:          0 :         PyRef valueRep( PyObject_Repr( excValue.get() ), SAL_NO_ACQUIRE );
     156 [ #  # ][ #  # ]:          0 :         buf.appendAscii( PyString_AsString( valueRep.get())).appendAscii( ", traceback follows\n" );
                 [ #  # ]
     157 [ #  # ][ #  # ]:          0 :         buf.appendAscii( PyString_AsString( str.get() ) );
     158         [ #  # ]:          0 :         buf.appendAscii( ")" );
     159 [ #  # ][ #  # ]:          0 :         throw RuntimeException( buf.makeStringAndClear(), Reference< XInterface > () );
     160                 :            :     }
     161         [ +  - ]:        112 :     PyRef dict( PyModule_GetDict( module.get() ) );
     162         [ +  - ]:        112 :     return dict;
     163                 :            : }
     164                 :            : 
     165                 :        112 : static void readLoggingConfig( sal_Int32 *pLevel, FILE **ppFile )
     166                 :            : {
     167                 :        112 :     *pLevel = LogLevel::NONE;
     168                 :        112 :     *ppFile = 0;
     169                 :        112 :     OUString fileName;
     170                 :            :     osl_getModuleURLFromFunctionAddress(
     171                 :            :         reinterpret_cast< oslGenericFunction >(readLoggingConfig),
     172         [ +  - ]:        112 :         (rtl_uString **) &fileName );
     173                 :        112 :     fileName = OUString( fileName.getStr(), fileName.lastIndexOf( '/' )+1 );
     174                 :        112 :     fileName += OUString(  SAL_CONFIGFILE("pyuno" ));
     175                 :        112 :     rtl::Bootstrap bootstrapHandle( fileName );
     176                 :            : 
     177                 :        112 :     OUString str;
     178         [ -  + ]:        112 :     if( bootstrapHandle.getFrom( USTR_ASCII( "PYUNO_LOGLEVEL" ), str ) )
     179                 :            :     {
     180         [ #  # ]:          0 :         if ( str == "NONE" )
     181                 :          0 :             *pLevel = LogLevel::NONE;
     182         [ #  # ]:          0 :         else if ( str == "CALL" )
     183                 :          0 :             *pLevel = LogLevel::CALL;
     184         [ #  # ]:          0 :         else if ( str == "ARGS" )
     185                 :          0 :             *pLevel = LogLevel::ARGS;
     186                 :            :         else
     187                 :            :         {
     188                 :            :             fprintf( stderr, "unknown loglevel %s\n",
     189 [ #  # ][ #  # ]:          0 :                      OUStringToOString( str, RTL_TEXTENCODING_UTF8 ).getStr() );
     190                 :            :         }
     191                 :            :     }
     192         [ -  + ]:        112 :     if( *pLevel > LogLevel::NONE )
     193                 :            :     {
     194                 :          0 :         *ppFile = stdout;
     195         [ #  # ]:          0 :         if( bootstrapHandle.getFrom( USTR_ASCII( "PYUNO_LOGTARGET" ), str ) )
     196                 :            :         {
     197         [ #  # ]:          0 :             if ( str == "stdout" )
     198                 :          0 :                 *ppFile = stdout;
     199         [ #  # ]:          0 :             else if ( str == "stderr" )
     200                 :          0 :                 *ppFile = stderr;
     201                 :            :             else
     202                 :            :             {
     203                 :            :                 oslProcessInfo data;
     204                 :          0 :                 data.Size = sizeof( data );
     205                 :            :                 osl_getProcessInfo(
     206         [ #  # ]:          0 :                     0 , osl_Process_IDENTIFIER , &data );
     207         [ #  # ]:          0 :                 osl_getSystemPathFromFileURL( str.pData, &str.pData);
     208 [ #  # ][ #  # ]:          0 :                 OString o = OUStringToOString( str, osl_getThreadTextEncoding() );
     209                 :          0 :                 o += ".";
     210                 :          0 :                 o += OString::valueOf( (sal_Int32)data.Ident );
     211                 :            : 
     212         [ #  # ]:          0 :                 *ppFile = fopen( o.getStr() , "w" );
     213         [ #  # ]:          0 :                 if ( *ppFile )
     214                 :            :                 {
     215                 :            :                     // do not buffer (useful if e.g. analyzing a crash)
     216                 :          0 :                     setvbuf( *ppFile, 0, _IONBF, 0 );
     217                 :            :                 }
     218                 :            :                 else
     219                 :            :                 {
     220                 :            :                     fprintf( stderr, "couldn't create file %s\n",
     221 [ #  # ][ #  # ]:          0 :                              OUStringToOString( str, RTL_TEXTENCODING_UTF8 ).getStr() );
     222                 :            : 
     223                 :          0 :                 }
     224                 :            :             }
     225                 :            :         }
     226                 :        112 :     }
     227                 :        112 : }
     228                 :            : 
     229                 :            : /*-------------------------------------------------------------------
     230                 :            :  RuntimeImpl implementations
     231                 :            :  *-------------------------------------------------------------------*/
     232                 :        112 : PyRef stRuntimeImpl::create( const Reference< XComponentContext > &ctx )
     233                 :            :     throw( com::sun::star::uno::RuntimeException )
     234                 :            : {
     235         [ +  - ]:        112 :     RuntimeImpl *me = PyObject_New (RuntimeImpl, &RuntimeImpl_Type);
     236         [ -  + ]:        112 :     if( ! me )
     237                 :            :         throw RuntimeException(
     238                 :            :             OUString(  "cannot instantiate pyuno::RuntimeImpl"  ),
     239         [ #  # ]:          0 :             Reference< XInterface > () );
     240                 :        112 :     me->cargo = 0;
     241                 :            :     // must use a different struct here, as the PyObject_New
     242                 :            :     // makes C++ unusable
     243 [ +  - ][ +  - ]:        112 :     RuntimeCargo *c = new RuntimeCargo();
     244         [ +  - ]:        112 :     readLoggingConfig( &(c->logLevel) , &(c->logFile) );
     245         [ +  - ]:        112 :     log( c, LogLevel::CALL, "Instantiating pyuno bridge" );
     246                 :            : 
     247                 :        112 :     c->valid = 1;
     248         [ +  - ]:        112 :     c->xContext = ctx;
     249                 :            :     c->xInvocation = Reference< XSingleServiceFactory > (
     250 [ +  - ][ +  - ]:        224 :         ctx->getServiceManager()->createInstanceWithContext(
                 [ +  - ]
     251                 :            :             OUString(  "com.sun.star.script.Invocation"  ),
     252                 :        112 :             ctx ),
     253 [ +  - ][ +  - ]:        112 :         UNO_QUERY );
                 [ +  - ]
     254         [ -  + ]:        112 :     if( ! c->xInvocation.is() )
     255                 :            :         throw RuntimeException(
     256                 :            :             OUString(  "pyuno: couldn't instantiate invocation service"  ),
     257         [ #  # ]:          0 :             Reference< XInterface > () );
     258                 :            : 
     259                 :            :     c->xTypeConverter = Reference< XTypeConverter > (
     260 [ +  - ][ +  - ]:        224 :         ctx->getServiceManager()->createInstanceWithContext(
                 [ +  - ]
     261                 :            :             OUString(  "com.sun.star.script.Converter"  ),
     262                 :        112 :             ctx ),
     263 [ +  - ][ +  - ]:        112 :         UNO_QUERY );
                 [ +  - ]
     264         [ -  + ]:        112 :     if( ! c->xTypeConverter.is() )
     265                 :            :         throw RuntimeException(
     266                 :            :             OUString(  "pyuno: couldn't instantiate typeconverter service" ),
     267         [ #  # ]:          0 :             Reference< XInterface > () );
     268                 :            : 
     269                 :            :     c->xCoreReflection = Reference< XIdlReflection > (
     270 [ +  - ][ +  - ]:        224 :         ctx->getServiceManager()->createInstanceWithContext(
                 [ +  - ]
     271                 :            :             OUString(  "com.sun.star.reflection.CoreReflection"  ),
     272                 :        112 :             ctx ),
     273 [ +  - ][ +  - ]:        112 :         UNO_QUERY );
                 [ +  - ]
     274         [ -  + ]:        112 :     if( ! c->xCoreReflection.is() )
     275                 :            :         throw RuntimeException(
     276                 :            :             OUString(  "pyuno: couldn't instantiate corereflection service" ),
     277         [ #  # ]:          0 :             Reference< XInterface > () );
     278                 :            : 
     279                 :            :     c->xAdapterFactory = Reference< XInvocationAdapterFactory2 > (
     280 [ +  - ][ +  - ]:        224 :         ctx->getServiceManager()->createInstanceWithContext(
                 [ +  - ]
     281                 :            :             OUString(  "com.sun.star.script.InvocationAdapterFactory"  ),
     282                 :        112 :             ctx ),
     283 [ +  - ][ +  - ]:        112 :         UNO_QUERY );
                 [ +  - ]
     284         [ -  + ]:        112 :     if( ! c->xAdapterFactory.is() )
     285                 :            :         throw RuntimeException(
     286                 :            :             OUString(  "pyuno: couldn't instantiate invocation adapter factory service" ),
     287         [ #  # ]:          0 :             Reference< XInterface > () );
     288                 :            : 
     289                 :            :     c->xIntrospection = Reference< XIntrospection > (
     290 [ +  - ][ +  - ]:        224 :         ctx->getServiceManager()->createInstanceWithContext(
                 [ +  - ]
     291                 :            :             OUString(  "com.sun.star.beans.Introspection"  ),
     292                 :        112 :             ctx ),
     293 [ +  - ][ +  - ]:        112 :         UNO_QUERY );
                 [ +  - ]
     294         [ -  + ]:        112 :     if( ! c->xIntrospection.is() )
     295                 :            :         throw RuntimeException(
     296                 :            :             OUString(  "pyuno: couldn't instantiate introspection service" ),
     297         [ #  # ]:          0 :             Reference< XInterface > () );
     298                 :            : 
     299 [ +  - ][ +  - ]:        112 :     Any a = ctx->getValueByName(OUString( "/singletons/com.sun.star.reflection.theTypeDescriptionManager" ) );
     300         [ +  - ]:        112 :     a >>= c->xTdMgr;
     301         [ -  + ]:        112 :     if( ! c->xTdMgr.is() )
     302                 :            :         throw RuntimeException(
     303                 :            :             OUString(  "pyuno: couldn't retrieve typedescriptionmanager" ),
     304         [ #  # ]:          0 :             Reference< XInterface > () );
     305                 :            : 
     306                 :        112 :     me->cargo =c;
     307                 :        112 :     return PyRef( reinterpret_cast< PyObject * > ( me ), SAL_NO_ACQUIRE );
     308                 :            : }
     309                 :            : 
     310                 :          0 : void  stRuntimeImpl::del(PyObject* self)
     311                 :            : {
     312                 :          0 :     RuntimeImpl *me = reinterpret_cast< RuntimeImpl * > ( self );
     313         [ #  # ]:          0 :     if( me->cargo->logFile )
     314                 :          0 :         fclose( me->cargo->logFile );
     315         [ #  # ]:          0 :     delete me->cargo;
     316                 :          0 :     PyObject_Del (self);
     317                 :          0 : }
     318                 :            : 
     319                 :            : 
     320                 :        112 : void Runtime::initialize( const Reference< XComponentContext > & ctx )
     321                 :            :     throw ( RuntimeException )
     322                 :            : {
     323                 :        112 :     PyRef globalDict, runtime;
     324         [ +  - ]:        112 :     getRuntimeImpl( globalDict , runtime );
     325                 :        112 :     RuntimeImpl *impl = reinterpret_cast< RuntimeImpl * > (runtime.get());
     326                 :            : 
     327 [ #  # ][ -  + ]:        112 :     if( runtime.is() && impl->cargo->valid )
                 [ -  + ]
     328                 :            :     {
     329                 :            :         throw RuntimeException( OUString( "pyuno runtime has already been initialized before"  ),
     330         [ #  # ]:          0 :                                 Reference< XInterface > () );
     331                 :            :     }
     332         [ +  - ]:        112 :     PyRef keep( RuntimeImpl::create( ctx ) );
     333         [ +  - ]:        112 :     PyDict_SetItemString( globalDict.get(), "pyuno_runtime" , keep.get() );
     334 [ +  - ][ +  - ]:        112 :     Py_XINCREF( keep.get() );
         [ +  - ][ +  - ]
     335                 :        112 : }
     336                 :            : 
     337                 :            : 
     338                 :        399 : bool Runtime::isInitialized() throw ( RuntimeException )
     339                 :            : {
     340                 :        399 :     PyRef globalDict, runtime;
     341         [ +  - ]:        399 :     getRuntimeImpl( globalDict , runtime );
     342                 :        399 :     RuntimeImpl *impl = reinterpret_cast< RuntimeImpl * > (runtime.get());
     343 [ +  - ][ +  - ]:        399 :     return runtime.is() && impl->cargo->valid;
         [ +  - ][ +  + ]
     344                 :            : }
     345                 :            : 
     346                 :     172306 : Runtime::Runtime() throw(  RuntimeException )
     347                 :     172306 :     : impl( 0 )
     348                 :            : {
     349                 :     172306 :     PyRef globalDict, runtime;
     350         [ +  - ]:     172306 :     getRuntimeImpl( globalDict , runtime );
     351         [ -  + ]:     172306 :     if( ! runtime.is() )
     352                 :            :     {
     353                 :            :         throw RuntimeException(
     354                 :            :             OUString( "pyuno runtime is not initialized, "
     355                 :            :                                                   "(the pyuno.bootstrap needs to be called before using any uno classes)"),
     356         [ #  # ]:          0 :             Reference< XInterface > () );
     357                 :            :     }
     358                 :     172306 :     impl = reinterpret_cast< RuntimeImpl * > (runtime.get());
     359 [ +  - ][ +  - ]:     172306 :     Py_XINCREF( runtime.get() );
                 [ +  - ]
     360                 :     172306 : }
     361                 :            : 
     362                 :          0 : Runtime::Runtime( const Runtime & r )
     363                 :            : {
     364                 :          0 :     impl = r.impl;
     365         [ #  # ]:          0 :     Py_XINCREF( reinterpret_cast< PyObject * >(impl) );
     366                 :          0 : }
     367                 :            : 
     368                 :     172306 : Runtime::~Runtime()
     369                 :            : {
     370 [ +  - ][ -  + ]:     172306 :     Py_XDECREF( reinterpret_cast< PyObject * >(impl) );
     371                 :     172306 : }
     372                 :            : 
     373                 :          0 : Runtime & Runtime::operator = ( const Runtime & r )
     374                 :            : {
     375                 :          0 :     PyRef temp( reinterpret_cast< PyObject * >(r.impl) );
     376         [ #  # ]:          0 :     Py_XINCREF( temp.get() );
     377 [ #  # ][ #  # ]:          0 :     Py_XDECREF( reinterpret_cast< PyObject * >(impl) );
                 [ #  # ]
     378                 :          0 :     impl = r.impl;
     379         [ #  # ]:          0 :     return *this;
     380                 :            : }
     381                 :            : 
     382                 :      84024 : PyRef Runtime::any2PyObject (const Any &a ) const
     383                 :            :     throw ( com::sun::star::script::CannotConvertException,
     384                 :            :             com::sun::star::lang::IllegalArgumentException,
     385                 :            :             RuntimeException)
     386                 :            : {
     387         [ -  + ]:      84024 :     if( ! impl->cargo->valid )
     388                 :            :     {
     389                 :            :         throw RuntimeException( OUString( "pyuno runtime must be initialized before calling any2PyObject" ),
     390         [ #  # ]:          0 :                                 Reference< XInterface > () );
     391                 :            :     }
     392                 :            : 
     393   [ +  -  -  +  :      84024 :     switch (a.getValueTypeClass ())
          -  -  -  -  -  
          +  -  -  -  +  
                +  +  - ]
     394                 :            :     {
     395                 :            :     case typelib_TypeClass_VOID:
     396                 :            :     {
     397                 :         48 :         Py_INCREF (Py_None);
     398                 :         48 :         return PyRef(Py_None);
     399                 :            :     }
     400                 :            :     case typelib_TypeClass_CHAR:
     401                 :            :     {
     402                 :          0 :         sal_Unicode c = *(sal_Unicode*)a.getValue();
     403                 :          0 :         return PyRef( PyUNO_char_new( c , *this ), SAL_NO_ACQUIRE );
     404                 :            :     }
     405                 :            :     case typelib_TypeClass_BOOLEAN:
     406                 :            :     {
     407                 :          0 :         sal_Bool b = sal_Bool();
     408 [ #  # ][ #  # ]:          0 :         if ((a >>= b) && b)
                 [ #  # ]
     409                 :          0 :             return Py_True;
     410                 :            :         else
     411                 :          0 :             return Py_False;
     412                 :            :     }
     413                 :            :     case typelib_TypeClass_BYTE:
     414                 :            :     case typelib_TypeClass_SHORT:
     415                 :            :     case typelib_TypeClass_UNSIGNED_SHORT:
     416                 :            :     case typelib_TypeClass_LONG:
     417                 :            :     {
     418                 :      24378 :         sal_Int32 l = 0;
     419                 :      24378 :         a >>= l;
     420         [ +  - ]:      24378 :         return PyRef( PyLong_FromLong (l), SAL_NO_ACQUIRE );
     421                 :            :     }
     422                 :            :     case typelib_TypeClass_UNSIGNED_LONG:
     423                 :            :     {
     424                 :          0 :         sal_uInt32 l = 0;
     425                 :          0 :         a >>= l;
     426         [ #  # ]:          0 :         return PyRef( PyLong_FromUnsignedLong (l), SAL_NO_ACQUIRE );
     427                 :            :     }
     428                 :            :     case typelib_TypeClass_HYPER:
     429                 :            :     {
     430                 :          0 :         sal_Int64 l = 0;
     431                 :          0 :         a >>= l;
     432         [ #  # ]:          0 :         return PyRef( PyLong_FromLongLong (l), SAL_NO_ACQUIRE);
     433                 :            :     }
     434                 :            :     case typelib_TypeClass_UNSIGNED_HYPER:
     435                 :            :     {
     436                 :          0 :         sal_uInt64 l = 0;
     437                 :          0 :         a >>= l;
     438         [ #  # ]:          0 :         return PyRef( PyLong_FromUnsignedLongLong (l), SAL_NO_ACQUIRE);
     439                 :            :     }
     440                 :            :     case typelib_TypeClass_FLOAT:
     441                 :            :     {
     442                 :          0 :         float f = 0.0;
     443                 :          0 :         a >>= f;
     444         [ #  # ]:          0 :         return PyRef(PyFloat_FromDouble (f), SAL_NO_ACQUIRE);
     445                 :            :     }
     446                 :            :     case typelib_TypeClass_DOUBLE:
     447                 :            :     {
     448                 :          0 :         double d = 0.0;
     449                 :          0 :         a >>= d;
     450         [ #  # ]:          0 :         return PyRef( PyFloat_FromDouble (d), SAL_NO_ACQUIRE);
     451                 :            :     }
     452                 :            :     case typelib_TypeClass_STRING:
     453                 :            :     {
     454                 :      45029 :         OUString tmp_ostr;
     455                 :      45029 :         a >>= tmp_ostr;
     456         [ +  - ]:      45029 :         return ustring2PyUnicode( tmp_ostr );
     457                 :            :     }
     458                 :            :     case typelib_TypeClass_TYPE:
     459                 :            :     {
     460                 :          0 :         Type t;
     461                 :          0 :         a >>= t;
     462         [ #  # ]:          0 :         OString o = OUStringToOString( t.getTypeName(), RTL_TEXTENCODING_ASCII_US );
     463                 :            :         return PyRef(
     464                 :            :             PyUNO_Type_new (
     465                 :            :                 o.getStr(),  (com::sun::star::uno::TypeClass)t.getTypeClass(), *this),
     466         [ #  # ]:          0 :             SAL_NO_ACQUIRE);
     467                 :            :     }
     468                 :            :     case typelib_TypeClass_ANY:
     469                 :            :     {
     470                 :            :         //I don't think this can happen.
     471                 :          0 :         Py_INCREF (Py_None);
     472                 :          0 :         return Py_None;
     473                 :            :     }
     474                 :            :     case typelib_TypeClass_ENUM:
     475                 :            :     {
     476                 :          0 :         sal_Int32 l = *(sal_Int32 *) a.getValue();
     477                 :          0 :         TypeDescription desc( a.getValueType() );
     478         [ #  # ]:          0 :         if( desc.is() )
     479                 :            :         {
     480                 :          0 :             desc.makeComplete();
     481                 :            :             typelib_EnumTypeDescription *pEnumDesc =
     482                 :          0 :                 (typelib_EnumTypeDescription *) desc.get();
     483         [ #  # ]:          0 :             for( int i = 0 ; i < pEnumDesc->nEnumValues ; i ++ )
     484                 :            :             {
     485         [ #  # ]:          0 :                 if( pEnumDesc->pEnumValues[i] == l )
     486                 :            :                 {
     487         [ #  # ]:          0 :                     OString v = OUStringToOString( pEnumDesc->ppEnumNames[i], RTL_TEXTENCODING_ASCII_US);
     488         [ #  # ]:          0 :                     OString e = OUStringToOString( pEnumDesc->aBase.pTypeName, RTL_TEXTENCODING_ASCII_US);
     489         [ #  # ]:          0 :                     return PyRef( PyUNO_Enum_new(e.getStr(),v.getStr(), *this ), SAL_NO_ACQUIRE );
     490                 :            :                 }
     491                 :            :             }
     492                 :            :         }
     493                 :          0 :         OUStringBuffer buf;
     494         [ #  # ]:          0 :         buf.appendAscii( "Any carries enum " );
     495         [ #  # ]:          0 :         buf.append( a.getValueType().getTypeName());
     496 [ #  # ][ #  # ]:          0 :         buf.appendAscii( " with invalid value " ).append( l );
     497 [ #  # ][ #  # ]:          0 :         throw RuntimeException( buf.makeStringAndClear() , Reference< XInterface > ()  );
     498                 :            :     }
     499                 :            :     case typelib_TypeClass_EXCEPTION:
     500                 :            :     case typelib_TypeClass_STRUCT:
     501                 :            :     {
     502         [ +  - ]:       7465 :         PyRef excClass = getClass( a.getValueType().getTypeName(), *this );
     503         [ +  - ]:       7465 :         PyRef value = PyRef( PyUNO_new_UNCHECKED (a, getImpl()->cargo->xInvocation), SAL_NO_ACQUIRE);
     504         [ +  - ]:       7465 :         PyRef argsTuple( PyTuple_New( 1 ) , SAL_NO_ACQUIRE );
     505         [ +  - ]:       7465 :         PyTuple_SetItem( argsTuple.get() , 0 , value.getAcquired() );
     506         [ +  - ]:       7465 :         PyRef ret( PyObject_CallObject( excClass.get() , argsTuple.get() ), SAL_NO_ACQUIRE );
     507         [ -  + ]:       7465 :         if( ! ret.is() )
     508                 :            :         {
     509                 :          0 :             OUStringBuffer buf;
     510         [ #  # ]:          0 :             buf.appendAscii( "Couldn't instantiate python representation of structered UNO type " );
     511         [ #  # ]:          0 :             buf.append( a.getValueType().getTypeName() );
     512 [ #  # ][ #  # ]:          0 :             throw RuntimeException( buf.makeStringAndClear(), Reference< XInterface > () );
     513                 :            :         }
     514                 :            : 
     515         [ +  + ]:       7465 :         if( com::sun::star::uno::TypeClass_EXCEPTION == a.getValueTypeClass() )
     516                 :            :         {
     517                 :            :             // add the message in a standard python way !
     518         [ +  - ]:       2802 :             PyRef args( PyTuple_New( 1 ), SAL_NO_ACQUIRE );
     519                 :            : 
     520                 :            :             // assuming that the Message is always the first member, wuuuu
     521                 :       2802 :             void *pData = (void*)a.getValue();
     522                 :       2802 :             OUString message = *(OUString * )pData;
     523         [ +  - ]:       2802 :             PyRef pymsg = ustring2PyString( message );
     524         [ +  - ]:       2802 :             PyTuple_SetItem( args.get(), 0 , pymsg.getAcquired() );
     525                 :            :             // the exception base functions want to have an "args" tuple,
     526                 :            :             // which contains the message
     527 [ +  - ][ +  - ]:       2802 :             PyObject_SetAttrString( ret.get(), "args", args.get() );
                 [ +  - ]
     528                 :            :         }
     529 [ +  - ][ +  - ]:       7465 :         return ret;
         [ +  - ][ +  - ]
                 [ +  - ]
     530                 :            :     }
     531                 :            :     case typelib_TypeClass_SEQUENCE:
     532                 :            :     {
     533         [ +  - ]:       4889 :         Sequence<Any> s;
     534                 :            : 
     535         [ +  - ]:       4889 :         Sequence< sal_Int8 > byteSequence;
     536 [ +  - ][ +  + ]:       4889 :         if( a >>= byteSequence )
     537                 :            :         {
     538                 :            :             // byte sequence is treated in a special way because of peformance reasons
     539                 :            :             // @since 0.9.2
     540         [ +  - ]:        212 :             return PyRef( PyUNO_ByteSequence_new( byteSequence, *this ), SAL_NO_ACQUIRE );
     541                 :            :         }
     542                 :            :         else
     543                 :            :         {
     544                 :       4677 :             Reference< XTypeConverter > tc = getImpl()->cargo->xTypeConverter;
     545                 :       4677 :             Reference< XSingleServiceFactory > ssf = getImpl()->cargo->xInvocation;
     546 [ +  - ][ +  - ]:       4677 :             tc->convertTo (a, ::getCppuType (&s)) >>= s;
         [ +  - ][ +  - ]
     547         [ +  - ]:       4677 :             PyRef tuple( PyTuple_New (s.getLength()), SAL_NO_ACQUIRE);
     548                 :       4677 :             int i=0;
     549                 :            :             try
     550                 :            :             {
     551         [ +  + ]:       4773 :                 for ( i = 0; i < s.getLength (); i++)
     552                 :            :                 {
     553                 :         96 :                     PyRef element;
     554 [ +  - ][ +  - ]:         96 :                     element = any2PyObject (tc->convertTo (s[i], s[i].getValueType() ));
         [ +  - ][ +  - ]
         [ +  - ][ +  - ]
                 [ +  - ]
     555                 :            :                     OSL_ASSERT( element.is() );
     556         [ +  - ]:         96 :                     PyTuple_SetItem( tuple.get(), i, element.getAcquired() );
     557         [ +  - ]:         96 :                 }
     558                 :            :             }
     559         [ #  # ]:          0 :             catch( com::sun::star::uno::Exception & )
     560                 :            :             {
     561         [ #  # ]:          0 :                 for( ; i < s.getLength() ; i ++ )
     562                 :            :                 {
     563                 :          0 :                     Py_INCREF( Py_None );
     564         [ #  # ]:          0 :                     PyTuple_SetItem( tuple.get(), i,  Py_None );
     565                 :            :                 }
     566                 :          0 :                 throw;
     567                 :            :             }
     568 [ +  - ][ +  - ]:       4677 :             return tuple;
     569 [ +  - ][ +  - ]:       4889 :         }
     570                 :            :     }
     571                 :            :     case typelib_TypeClass_INTERFACE:
     572                 :            :     {
     573                 :       2215 :         Reference< XUnoTunnel > tunnel;
     574         [ +  - ]:       2215 :         a >>= tunnel;
     575         [ +  + ]:       2215 :         if( tunnel.is() )
     576                 :            :         {
     577 [ +  - ][ +  - ]:        130 :             sal_Int64 that = tunnel->getSomething( ::pyuno::Adapter::getUnoTunnelImplementationId() );
         [ +  - ][ +  - ]
     578         [ -  + ]:        130 :             if( that )
     579         [ #  # ]:          0 :                 return ((Adapter*)sal::static_int_cast< sal_IntPtr >(that))->getWrappedObject();
     580                 :            :         }
     581                 :            :         //This is just like the struct case:
     582         [ +  - ]:       2215 :         return PyRef( PyUNO_new (a, getImpl()->cargo->xInvocation), SAL_NO_ACQUIRE );
     583                 :            :     }
     584                 :            :     default:
     585                 :            :     {
     586                 :          0 :         OUStringBuffer buf;
     587         [ #  # ]:          0 :         buf.appendAscii( "Unknonwn UNO type class " );
     588         [ #  # ]:          0 :         buf.append( (sal_Int32 ) a.getValueTypeClass() );
     589 [ #  # ][ #  # ]:      84024 :         throw RuntimeException(buf.makeStringAndClear( ), Reference< XInterface > () );
     590                 :            :     }
     591                 :            :     }
     592                 :            : }
     593                 :            : 
     594                 :        356 : static Sequence< Type > invokeGetTypes( const Runtime & r , PyObject * o )
     595                 :            : {
     596         [ +  - ]:        356 :     Sequence< Type > ret;
     597                 :            : 
     598         [ +  - ]:        356 :     PyRef method( PyObject_GetAttrString( o , "getTypes" ), SAL_NO_ACQUIRE );
     599         [ +  - ]:        356 :     raiseInvocationTargetExceptionWhenNeeded( r );
     600 [ +  - ][ +  - ]:        356 :     if( method.is() && PyCallable_Check( method.get() ) )
         [ +  - ][ +  - ]
     601                 :            :     {
     602         [ +  - ]:        356 :         PyRef types( PyObject_CallObject( method.get(), 0 ) , SAL_NO_ACQUIRE );
     603         [ +  - ]:        356 :         raiseInvocationTargetExceptionWhenNeeded( r );
     604 [ +  - ][ +  - ]:        356 :         if( types.is() && PyTuple_Check( types.get() ) )
                 [ +  - ]
     605                 :            :         {
     606         [ +  - ]:        356 :             int size = PyTuple_Size( types.get() );
     607                 :            : 
     608                 :            :             // add the XUnoTunnel interface  for uno object identity concept (hack)
     609         [ +  - ]:        356 :             ret.realloc( size + 1 );
     610         [ +  + ]:       1814 :             for( int i = 0 ; i < size ; i ++ )
     611                 :            :             {
     612 [ +  - ][ +  - ]:       1458 :                 Any a = r.pyObject2Any(PyTuple_GetItem(types.get(),i));
                 [ +  - ]
     613         [ +  - ]:       1458 :                 a >>= ret[i];
     614                 :       1458 :             }
     615 [ +  - ][ +  - ]:        356 :             ret[size] = getCppuType( (Reference< com::sun::star::lang::XUnoTunnel> *) 0 );
     616         [ +  - ]:        356 :         }
     617                 :            :     }
     618         [ +  - ]:        356 :     return ret;
     619                 :            : }
     620                 :            : 
     621                 :      79202 : Any Runtime::pyObject2Any ( const PyRef & source, enum ConversionMode mode ) const
     622                 :            :     throw ( com::sun::star::uno::RuntimeException )
     623                 :            : {
     624         [ -  + ]:      79202 :     if( ! impl->cargo->valid )
     625                 :            :     {
     626                 :            :         throw RuntimeException( OUString( "pyuno runtime must be initialized before calling any2PyObject" ),
     627         [ #  # ]:          0 :                                 Reference< XInterface > () );
     628                 :            :     }
     629                 :            : 
     630                 :      79202 :     Any a;
     631                 :      79202 :     PyObject *o = source.get();
     632         [ +  - ]:      79202 :     if( Py_None == o )
     633                 :            :     {
     634                 :            : 
     635                 :            :     }
     636                 :            :     // In Python 3, there is no PyInt type.
     637                 :            : #if PY_MAJOR_VERSION < 3
     638         [ +  + ]:      79202 :     else if (PyInt_Check (o))
     639                 :            :     {
     640         [ +  + ]:       1034 :         if( o == Py_True )
     641                 :            :         {
     642                 :         34 :             sal_Bool b = sal_True;
     643         [ +  - ]:         34 :             a = Any( &b, getBooleanCppuType() );
     644                 :            :         }
     645         [ -  + ]:       1000 :         else if ( o == Py_False )
     646                 :            :         {
     647                 :          0 :             sal_Bool b = sal_False;
     648         [ #  # ]:          0 :             a = Any( &b, getBooleanCppuType() );
     649                 :            :         }
     650                 :            :         else
     651                 :            :         {
     652         [ +  - ]:       1000 :             sal_Int32 l = (sal_Int32) PyLong_AsLong( o );
     653 [ +  - ][ +  - ]:       1000 :             if( l < 128 && l >= -128 )
     654                 :            :             {
     655                 :       1000 :                 sal_Int8 b = (sal_Int8 ) l;
     656         [ +  - ]:       1000 :                 a <<= b;
     657                 :            :             }
     658 [ #  # ][ #  # ]:          0 :             else if( l <= 0x7fff && l >= -0x8000 )
     659                 :            :             {
     660                 :          0 :                 sal_Int16 s = (sal_Int16) l;
     661         [ #  # ]:          0 :                 a <<= s;
     662                 :            :             }
     663                 :            :             else
     664                 :            :             {
     665         [ #  # ]:       1000 :                 a <<= l;
     666                 :            :             }
     667                 :            :         }
     668                 :            :     }
     669                 :            : #endif /* PY_MAJOR_VERSION < 3 */
     670         [ +  + ]:      78168 :     else if (PyLong_Check (o))
     671                 :            :     {
     672                 :            : #if PY_MAJOR_VERSION >= 3
     673                 :            :         // Convert the Python 3 booleans that are actually of type PyLong.
     674                 :            :         if(o == Py_True)
     675                 :            :         {
     676                 :            :             sal_Bool b = sal_True;
     677                 :            :             a = Any(&b, getBooleanCppuType());
     678                 :            :         }
     679                 :            :         else if(o == Py_False)
     680                 :            :         {
     681                 :            :             sal_Bool b = sal_False;
     682                 :            :             a = Any(&b, getBooleanCppuType());
     683                 :            :         }
     684                 :            :         else
     685                 :            :         {
     686                 :            : #endif /* PY_MAJOR_VERSION >= 3 */
     687         [ +  - ]:      15639 :         sal_Int64 l = (sal_Int64)PyLong_AsLong (o);
     688 [ +  + ][ +  - ]:      15639 :         if( l < 128 && l >= -128 )
     689                 :            :         {
     690                 :      10690 :             sal_Int8 b = (sal_Int8 ) l;
     691         [ +  - ]:      10690 :             a <<= b;
     692                 :            :         }
     693 [ +  - ][ +  - ]:       4949 :         else if( l <= 0x7fff && l >= -0x8000 )
     694                 :            :         {
     695                 :       4949 :             sal_Int16 s = (sal_Int16) l;
     696         [ +  - ]:       4949 :             a <<= s;
     697                 :            :         }
     698 [ #  # ][ #  # ]:          0 :         else if( l <= SAL_CONST_INT64(0x7fffffff) &&
     699                 :            :                  l >= -SAL_CONST_INT64(0x80000000) )
     700                 :            :         {
     701                 :          0 :             sal_Int32 l32 = (sal_Int32) l;
     702         [ #  # ]:          0 :             a <<= l32;
     703                 :            :         }
     704                 :            :         else
     705                 :            :         {
     706         [ #  # ]:      15639 :             a <<= l;
     707                 :            :         }
     708                 :            : #if PY_MAJOR_VERSION >= 3
     709                 :            :         }
     710                 :            : #endif
     711                 :            :     }
     712 [ +  - ][ +  - ]:      62529 :     else if (PyFloat_Check (o))
         [ -  + ][ -  + ]
     713                 :            :     {
     714         [ #  # ]:          0 :         double d = PyFloat_AsDouble (o);
     715         [ #  # ]:          0 :         a <<= d;
     716                 :            :     }
     717 [ +  + ][ +  + ]:      62529 :     else if (PyString_Check(o) || PyUnicode_Check(o))
     718                 :            :     {
     719 [ +  - ][ +  - ]:      25876 :         a <<= pyString2ustring(o);
     720                 :            :     }
     721         [ +  + ]:      36653 :     else if (PyTuple_Check (o))
     722                 :            :     {
     723 [ +  - ][ +  - ]:      17608 :         Sequence<Any> s (PyTuple_Size (o));
     724 [ +  - ][ +  + ]:      28428 :         for (int i = 0; i < PyTuple_Size (o); i++)
     725                 :            :         {
     726 [ +  - ][ +  - ]:      10820 :             s[i] = pyObject2Any (PyTuple_GetItem (o, i), mode );
         [ +  - ][ +  - ]
     727                 :            :         }
     728 [ +  - ][ +  - ]:      17608 :         a <<= s;
     729                 :            :     }
     730                 :            :     else
     731                 :            :     {
     732         [ +  - ]:      19045 :         Runtime runtime;
     733                 :            :         // should be removed, in case ByteSequence gets derived from String
     734 [ +  - ][ +  - ]:      19045 :         if( PyObject_IsInstance( o, getByteSequenceClass( runtime ).get() ) )
         [ +  - ][ +  + ]
     735                 :            :         {
     736         [ +  - ]:         96 :             PyRef str(PyObject_GetAttrString( o , "value" ),SAL_NO_ACQUIRE);
     737         [ +  - ]:         96 :             Sequence< sal_Int8 > seq;
     738         [ +  - ]:         96 :             if( PyString_Check( str.get() ) )
     739                 :            :             {
     740                 :            :                 seq = Sequence<sal_Int8 > (
     741 [ +  - ][ +  - ]:         96 :                     (sal_Int8*) PyString_AsString(str.get()), PyString_Size(str.get()));
         [ +  - ][ +  - ]
                 [ +  - ]
     742                 :            :             }
     743 [ +  - ][ +  - ]:         96 :             a <<= seq;
                 [ +  - ]
     744                 :            :         }
     745                 :            :         else
     746 [ +  - ][ +  - ]:      18949 :         if( PyObject_IsInstance( o, getTypeClass( runtime ).get() ) )
         [ +  - ][ +  + ]
     747                 :            :         {
     748         [ +  - ]:       2034 :             Type t = PyType2Type( o );
     749         [ +  - ]:       2034 :             a <<= t;
     750                 :            :         }
     751 [ +  - ][ +  - ]:      16915 :         else if( PyObject_IsInstance( o, getEnumClass( runtime ).get() ) )
         [ +  - ][ -  + ]
     752                 :            :         {
     753         [ #  # ]:          0 :             a = PyEnum2Enum( o );
     754                 :            :         }
     755 [ +  - ][ +  + ]:      16915 :         else if( isInstanceOfStructOrException( o ) )
     756                 :            :         {
     757         [ +  - ]:      11800 :             PyRef struc(PyObject_GetAttrString( o , "value" ),SAL_NO_ACQUIRE);
     758                 :      11800 :             PyUNO * obj = (PyUNO*)struc.get();
     759         [ +  - ]:      11800 :             Reference< XMaterialHolder > holder( obj->members->xInvocation, UNO_QUERY );
     760         [ +  - ]:      11800 :             if( holder.is( ) )
     761 [ +  - ][ +  - ]:      11800 :                 a = holder->getMaterial();
     762                 :            :             else
     763                 :            :             {
     764                 :            :                 throw RuntimeException(
     765                 :            :                     USTR_ASCII( "struct or exception wrapper does not support XMaterialHolder" ),
     766         [ #  # ]:      11800 :                     Reference< XInterface > () );
     767         [ +  - ]:      11800 :             }
     768                 :            :         }
     769 [ +  - ][ +  - ]:       5115 :         else if( PyObject_IsInstance( o, getPyUnoClass().get() ) )
         [ +  - ][ +  + ]
     770                 :            :         {
     771                 :            :             PyUNO* o_pi;
     772                 :        130 :             o_pi = (PyUNO*) o;
     773   [ +  -  -  + ]:        260 :             if (o_pi->members->wrappedObject.getValueTypeClass () ==
                 [ -  + ]
     774                 :            :                 com::sun::star::uno::TypeClass_STRUCT ||
     775                 :        130 :                 o_pi->members->wrappedObject.getValueTypeClass () ==
     776                 :            :                 com::sun::star::uno::TypeClass_EXCEPTION)
     777                 :            :             {
     778         [ #  # ]:          0 :                 Reference<XMaterialHolder> my_mh (o_pi->members->xInvocation, UNO_QUERY);
     779                 :            : 
     780         [ #  # ]:          0 :                 if (!my_mh.is ())
     781                 :            :                 {
     782                 :            :                     throw RuntimeException(
     783                 :            :                         USTR_ASCII( "struct wrapper does not support XMaterialHolder" ),
     784         [ #  # ]:          0 :                         Reference< XInterface > () );
     785                 :            :                 }
     786                 :            :                 else
     787 [ #  # ][ #  # ]:          0 :                     a = my_mh->getMaterial ();
     788                 :            :             }
     789                 :            :             else
     790                 :            :             {
     791                 :        130 :                 a = o_pi->members->wrappedObject;
     792                 :            :             }
     793                 :            :         }
     794 [ +  - ][ +  - ]:       4985 :         else if( PyObject_IsInstance( o, getCharClass( runtime ).get() ) )
         [ +  - ][ -  + ]
     795                 :            :         {
     796         [ #  # ]:          0 :             sal_Unicode c = PyChar2Unicode( o );
     797         [ #  # ]:          0 :             a.setValue( &c, getCharCppuType( ));
     798                 :            :         }
     799 [ +  - ][ +  - ]:       4985 :         else if( PyObject_IsInstance( o, getAnyClass( runtime ).get() ) )
         [ +  - ][ -  + ]
     800                 :            :         {
     801         [ #  # ]:          0 :             if( ACCEPT_UNO_ANY == mode )
     802                 :            :             {
     803 [ #  # ][ #  # ]:          0 :                 a = pyObject2Any( PyRef( PyObject_GetAttrString( o , "value" ), SAL_NO_ACQUIRE) );
                 [ #  # ]
     804                 :          0 :                 Type t;
     805 [ #  # ][ #  # ]:          0 :                 pyObject2Any( PyRef( PyObject_GetAttrString( o, "type" ), SAL_NO_ACQUIRE ) ) >>= t;
                 [ #  # ]
     806                 :            : 
     807                 :            :                 try
     808                 :            :                 {
     809 [ #  # ][ #  # ]:          0 :                     a = getImpl()->cargo->xTypeConverter->convertTo( a, t );
     810                 :            :                 }
     811         [ #  # ]:          0 :                 catch( const com::sun::star::uno::Exception & e )
     812                 :            :                 {
     813         [ #  # ]:          0 :                     throw RuntimeException( e.Message, e.Context );
     814                 :          0 :                 }
     815                 :            :             }
     816                 :            :             else
     817                 :            :             {
     818                 :            :                 throw RuntimeException(
     819                 :            :                     OUString( "uno.Any instance not accepted during method call, "
     820                 :            :                                   "use uno.invoke instead"  ),
     821         [ #  # ]:          0 :                     Reference< XInterface > () );
     822                 :            :             }
     823                 :            :         }
     824                 :            :         else
     825                 :            :         {
     826                 :       4985 :             Reference< XInterface > mappedObject;
     827                 :       4985 :             Reference< XInvocation > adapterObject;
     828                 :            : 
     829                 :            :             // instance already mapped out to the world ?
     830 [ +  - ][ +  - ]:       4985 :             PyRef2Adapter::iterator ii = impl->cargo->mappedObjects.find( PyRef( o ) );
     831 [ +  - ][ +  + ]:       4985 :             if( ii != impl->cargo->mappedObjects.end() )
     832                 :            :             {
     833 [ +  - ][ +  - ]:       4629 :                 adapterObject = ii->second;
                 [ +  - ]
     834                 :            :             }
     835                 :            : 
     836         [ +  + ]:       4985 :             if( adapterObject.is() )
     837                 :            :             {
     838                 :            :                 // object got already bridged !
     839         [ +  - ]:       4629 :                 Reference< com::sun::star::lang::XUnoTunnel > tunnel( adapterObject, UNO_QUERY );
     840                 :            : 
     841                 :            :                 Adapter *pAdapter = ( Adapter * )
     842                 :            :                     sal::static_int_cast< sal_IntPtr >(
     843         [ +  - ]:       4629 :                         tunnel->getSomething(
     844 [ +  - ][ +  - ]:       4629 :                             ::pyuno::Adapter::getUnoTunnelImplementationId() ) );
                 [ +  - ]
     845                 :            : 
     846         [ +  - ]:       4629 :                 mappedObject = impl->cargo->xAdapterFactory->createAdapter(
     847 [ +  - ][ +  - ]:       4629 :                     adapterObject, pAdapter->getWrappedTypes() );
         [ +  - ][ +  - ]
     848                 :            :             }
     849                 :            :             else
     850                 :            :             {
     851         [ +  - ]:        356 :                 Sequence< Type > interfaces = invokeGetTypes( *this, o );
     852         [ +  - ]:        356 :                 if( interfaces.getLength() )
     853                 :            :                 {
     854 [ +  - ][ +  - ]:        356 :                     Adapter *pAdapter = new Adapter( o, interfaces );
     855                 :            :                     mappedObject =
     856         [ +  - ]:        356 :                         getImpl()->cargo->xAdapterFactory->createAdapter(
     857 [ +  - ][ +  - ]:        356 :                             pAdapter, interfaces );
         [ +  - ][ +  - ]
     858                 :            : 
     859                 :            :                     // keep a list of exported objects to ensure object identity !
     860 [ +  - ][ +  - ]:        712 :                     impl->cargo->mappedObjects[ PyRef(o) ] =
     861 [ +  - ][ +  - ]:       1068 :                         com::sun::star::uno::WeakReference< XInvocation > ( pAdapter );
         [ +  - ][ +  - ]
                 [ +  - ]
     862         [ +  - ]:        356 :                 }
     863                 :            :             }
     864         [ +  - ]:       4985 :             if( mappedObject.is() )
     865                 :            :             {
     866         [ +  - ]:       4985 :                 a = com::sun::star::uno::makeAny( mappedObject );
     867                 :            :             }
     868                 :            :             else
     869                 :            :             {
     870                 :          0 :                 OUStringBuffer buf;
     871         [ #  # ]:          0 :                 buf.appendAscii( "Couldn't convert " );
     872         [ #  # ]:          0 :                 PyRef reprString( PyObject_Str( o ) , SAL_NO_ACQUIRE );
     873 [ #  # ][ #  # ]:          0 :                 buf.appendAscii( PyString_AsString( reprString.get() ) );
     874         [ #  # ]:          0 :                 buf.appendAscii( " to a UNO type" );
     875 [ #  # ][ #  # ]:          0 :                 throw RuntimeException( buf.makeStringAndClear(), Reference< XInterface > () );
     876                 :       4985 :             }
     877         [ +  - ]:      19045 :         }
     878                 :            :     }
     879                 :      79202 :     return a;
     880                 :            : }
     881                 :            : 
     882                 :          0 : Any Runtime::extractUnoException( const PyRef & excType, const PyRef &excValue, const PyRef &excTraceback) const
     883                 :            : {
     884                 :          0 :     OUString str;
     885                 :          0 :     Any ret;
     886         [ #  # ]:          0 :     if( excTraceback.is() )
     887                 :            :     {
     888         [ #  # ]:          0 :         Exception e;
     889                 :          0 :         PyRef unoModule;
     890         [ #  # ]:          0 :         if ( impl )
     891                 :            :         {
     892                 :            :             try
     893                 :            :             {
     894 [ #  # ][ #  # ]:          0 :                 unoModule = impl->cargo->getUnoModule();
                 [ #  # ]
     895                 :            :             }
     896   [ #  #  #  # ]:          0 :             catch (const Exception &ei)
     897                 :            :             {
     898         [ #  # ]:          0 :                 e=ei;
     899                 :            :             }
     900                 :            :         }
     901         [ #  # ]:          0 :         if( unoModule.is() )
     902                 :            :         {
     903                 :            :             PyRef extractTraceback(
     904         [ #  # ]:          0 :                 PyDict_GetItemString(unoModule.get(),"_uno_extract_printable_stacktrace" ) );
     905                 :            : 
     906 [ #  # ][ #  # ]:          0 :             if( PyCallable_Check(extractTraceback.get()) )
     907                 :            :             {
     908         [ #  # ]:          0 :                 PyRef args( PyTuple_New( 1), SAL_NO_ACQUIRE );
     909         [ #  # ]:          0 :                 PyTuple_SetItem( args.get(), 0, excTraceback.getAcquired() );
     910         [ #  # ]:          0 :                 PyRef pyStr( PyObject_CallObject( extractTraceback.get(),args.get() ), SAL_NO_ACQUIRE);
     911 [ #  # ][ #  # ]:          0 :                 str = rtl::OUString::createFromAscii( PyString_AsString(pyStr.get()) );
                 [ #  # ]
     912                 :            :             }
     913                 :            :             else
     914                 :            :             {
     915                 :          0 :                 str = OUString("Couldn't find uno._uno_extract_printable_stacktrace");
     916         [ #  # ]:          0 :             }
     917                 :            :         }
     918                 :            :         else
     919                 :            :         {
     920                 :          0 :             str = OUString("Could not load uno.py, no stacktrace available");
     921         [ #  # ]:          0 :             if ( !e.Message.isEmpty() )
     922                 :            :             {
     923                 :          0 :                 str += OUString (" (Error loading uno.py: ");
     924                 :          0 :                 str += e.Message;
     925                 :          0 :                 str += OUString (")");
     926                 :            :             }
     927 [ #  # ][ #  # ]:          0 :         }
     928                 :            : 
     929                 :            :     }
     930                 :            :     else
     931                 :            :     {
     932                 :            :         // it may occur, that no traceback is given (e.g. only native code below)
     933                 :          0 :         str = OUString(  "no traceback available"  );
     934                 :            :     }
     935                 :            : 
     936 [ #  # ][ #  # ]:          0 :     if( isInstanceOfStructOrException( excValue.get() ) )
     937                 :            :     {
     938         [ #  # ]:          0 :         ret = pyObject2Any( excValue );
     939                 :            :     }
     940                 :            :     else
     941                 :            :     {
     942                 :          0 :         OUStringBuffer buf;
     943         [ #  # ]:          0 :         PyRef typeName( PyObject_Str( excType.get() ), SAL_NO_ACQUIRE );
     944         [ #  # ]:          0 :         if( typeName.is() )
     945                 :            :         {
     946 [ #  # ][ #  # ]:          0 :             buf.appendAscii( PyString_AsString( typeName.get() ) );
     947                 :            :         }
     948                 :            :         else
     949                 :            :         {
     950         [ #  # ]:          0 :             buf.appendAscii( "no typename available" );
     951                 :            :         }
     952         [ #  # ]:          0 :         buf.appendAscii( ": " );
     953         [ #  # ]:          0 :         PyRef valueRep( PyObject_Str( excValue.get() ), SAL_NO_ACQUIRE );
     954         [ #  # ]:          0 :         if( valueRep.is() )
     955                 :            :         {
     956 [ #  # ][ #  # ]:          0 :             buf.appendAscii( PyString_AsString( valueRep.get()));
     957                 :            :         }
     958                 :            :         else
     959                 :            :         {
     960         [ #  # ]:          0 :             buf.appendAscii( "Couldn't convert exception value to a string" );
     961                 :            :         }
     962         [ #  # ]:          0 :         buf.appendAscii( ", traceback follows\n" );
     963         [ #  # ]:          0 :         if( !str.isEmpty() )
     964                 :            :         {
     965         [ #  # ]:          0 :             buf.append( str );
     966         [ #  # ]:          0 :             buf.appendAscii( "\n" );
     967                 :            :         }
     968                 :            :         else
     969                 :            :         {
     970         [ #  # ]:          0 :             buf.appendAscii( ", no traceback available\n" );
     971                 :            :         }
     972         [ #  # ]:          0 :         RuntimeException e;
     973         [ #  # ]:          0 :         e.Message = buf.makeStringAndClear();
     974                 :            : #if OSL_DEBUG_LEVEL > 0
     975                 :            :         fprintf( stderr, "Python exception: %s\n",
     976                 :            :                  rtl::OUStringToOString(e.Message, RTL_TEXTENCODING_UTF8).getStr() );
     977                 :            : #endif
     978 [ #  # ][ #  # ]:          0 :         ret = com::sun::star::uno::makeAny( e );
         [ #  # ][ #  # ]
     979                 :            :     }
     980                 :          0 :     return ret;
     981                 :            : }
     982                 :            : 
     983                 :            : 
     984                 :            : static const char * g_NUMERICID = "pyuno.lcNumeric";
     985                 :        112 : static ::std::vector< rtl::OString > g_localeList;
     986                 :            : 
     987                 :       5835 : static const char *ensureUnlimitedLifetime( const char *str )
     988                 :            : {
     989                 :       5835 :     int size = g_localeList.size();
     990                 :            :     int i;
     991         [ +  + ]:       5861 :     for( i = 0 ; i < size ; i ++ )
     992                 :            :     {
     993         [ +  + ]:       5747 :         if( 0 == strcmp( g_localeList[i].getStr(), str ) )
     994                 :       5721 :             break;
     995                 :            :     }
     996         [ +  + ]:       5835 :     if( i == size )
     997                 :            :     {
     998         [ +  - ]:        114 :         g_localeList.push_back( str );
     999                 :            :     }
    1000                 :       5835 :     return g_localeList[i].getStr();
    1001                 :            : }
    1002                 :            : 
    1003                 :            : 
    1004                 :       5835 : PyThreadAttach::PyThreadAttach( PyInterpreterState *interp)
    1005                 :            :     throw ( com::sun::star::uno::RuntimeException )
    1006                 :            : {
    1007         [ +  - ]:       5835 :     tstate = PyThreadState_New( interp );
    1008         [ -  + ]:       5835 :     if( !tstate  )
    1009                 :            :         throw RuntimeException(
    1010                 :            :             OUString( "Couldn't create a pythreadstate"  ),
    1011         [ #  # ]:          0 :             Reference< XInterface > () );
    1012         [ +  - ]:       5835 :     PyEval_AcquireThread( tstate);
    1013                 :            :     // set LC_NUMERIC to "C"
    1014                 :            :     const char * oldLocale =
    1015         [ +  - ]:       5835 :         ensureUnlimitedLifetime( setlocale( LC_NUMERIC, 0 )  );
    1016                 :       5835 :     setlocale( LC_NUMERIC, "C" );
    1017                 :            :     PyRef locale( // python requires C locale
    1018         [ +  - ]:       5835 :         PyLong_FromVoidPtr( (void*)oldLocale ), SAL_NO_ACQUIRE);
    1019                 :            :     PyDict_SetItemString(
    1020 [ +  - ][ +  - ]:       5835 :         PyThreadState_GetDict(), g_NUMERICID, locale.get() );
                 [ +  - ]
    1021                 :       5835 : }
    1022                 :            : 
    1023                 :       5835 : PyThreadAttach::~PyThreadAttach()
    1024                 :            : {
    1025                 :            :     PyObject *value =
    1026                 :       5835 :         PyDict_GetItemString( PyThreadState_GetDict( ), g_NUMERICID );
    1027         [ +  - ]:       5835 :     if( value )
    1028                 :       5835 :         setlocale( LC_NUMERIC, (const char * ) PyLong_AsVoidPtr( value ) );
    1029                 :       5835 :     PyThreadState_Clear( tstate );
    1030                 :       5835 :     PyEval_ReleaseThread( tstate );
    1031                 :       5835 :     PyThreadState_Delete( tstate );
    1032                 :            : 
    1033                 :       5835 : }
    1034                 :            : 
    1035                 :     137135 : PyThreadDetach::PyThreadDetach() throw ( com::sun::star::uno::RuntimeException )
    1036                 :            : {
    1037                 :     137135 :     tstate = PyThreadState_Get();
    1038                 :            :     PyObject *value =
    1039                 :     137135 :         PyDict_GetItemString( PyThreadState_GetDict( ), g_NUMERICID );
    1040         [ +  - ]:     137135 :     if( value )
    1041                 :     137135 :         setlocale( LC_NUMERIC, (const char * ) PyLong_AsVoidPtr( value ) );
    1042                 :     137135 :     PyEval_ReleaseThread( tstate );
    1043                 :     137135 : }
    1044                 :            : 
    1045                 :            :     /** Acquires the global interpreter lock again
    1046                 :            : 
    1047                 :            :     */
    1048                 :     137135 : PyThreadDetach::~PyThreadDetach()
    1049                 :            : {
    1050                 :     137135 :     PyEval_AcquireThread( tstate );
    1051                 :            : //     PyObject *value =
    1052                 :            : //         PyDict_GetItemString( PyThreadState_GetDict( ), g_NUMERICID );
    1053                 :            : 
    1054                 :            :     // python requires C LC_NUMERIC locale,
    1055                 :            :     // always set even when it is already "C"
    1056                 :     137135 :     setlocale( LC_NUMERIC, "C" );
    1057                 :     137135 : }
    1058                 :            : 
    1059                 :            : 
    1060                 :      70023 : PyRef RuntimeCargo::getUnoModule()
    1061                 :            : {
    1062         [ +  + ]:      70023 :     if( ! dictUnoModule.is() )
    1063                 :            :     {
    1064         [ +  - ]:        112 :         dictUnoModule = importUnoModule();
    1065                 :            :     }
    1066                 :      70023 :     return dictUnoModule;
    1067                 :            : }
    1068 [ +  - ][ +  - ]:        336 : }
    1069                 :            : 
    1070                 :            : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10