1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 #ifndef _PYUNO_PYUNO_HXX_ 23 #define _PYUNO_PYUNO_HXX_ 24 25 #ifndef Py_PYTHON_H 26 #if defined _MSC_VER 27 #pragma warning(push, 1) 28 #endif 29 #ifdef _DEBUG 30 #undef _DEBUG 31 #include <Python.h> 32 #define _DEBUG 33 #else 34 #include <Python.h> 35 #endif // #ifdef _DEBUG 36 #if defined _MSC_VER 37 #pragma warning(pop) 38 #endif 39 #endif // #ifdef Py_PYTHON_H 40 41 // Compatibility for older system Python (2.6 and previous) 42 #ifndef PyVarObject_HEAD_INIT 43 #define PyVarObject_HEAD_INIT(type, size) \ 44 PyObject_HEAD_INIT(type) size, 45 #endif 46 // define PyBytes_* as the equivalent string type methods. 47 #ifndef PyBytes_Check 48 #define PyBytes_Check PyString_Check 49 #define PyBytes_AsString PyString_AsString 50 #define PyBytes_FromString PyString_FromString 51 #define PyBytes_Size PyString_Size 52 #define PyBytes_FromStringAndSize PyString_FromStringAndSize 53 #endif 54 55 #include <com/sun/star/uno/XComponentContext.hpp> 56 #include <com/sun/star/script/CannotConvertException.hpp> 57 #include <com/sun/star/lang/IllegalArgumentException.hpp> 58 59 /** 60 External interface of the Python UNO bridge. 61 62 This is a C++ interface, because the core UNO components 63 invocation and proxyfactory are used to implement the bridge. 64 65 This interface is somewhat private and my change in future. 66 67 A scripting framework implementation may use this interface 68 to do the necessary conversions. 69 */ 70 71 #ifdef WIN32 72 #define PY_DLLEXPORT __declspec(dllexport) 73 #else 74 #define PY_DLLEXPORT 75 #endif 76 77 /** function called by the python runtime to initialize the 78 pyuno module. 79 80 preconditions: python has been initialized before and 81 the global interpreter lock is held 82 */ 83 extern "C" PY_DLLEXPORT void SAL_CALL initpyuno(); 84 85 86 namespace pyuno 87 { 88 89 /** Helper class for keeping references to python objects. 90 BEWARE: Look up every python function you use to check 91 wether you get an acquired or not acquired object pointer 92 (python terminus for a not acquired object pointer 93 is 'borrowed reference'). Use in the acquired pointer cases the 94 PyRef( pointer, SAL_NO_ACQUIRE) ctor. 95 96 precondition: python has been initialized before and 97 the global interpreter lock is held 98 99 */ 100 class PyRef 101 { 102 PyObject *m; 103 public: PyRef()104 PyRef () : m(0) {} PyRef(PyObject * p)105 PyRef( PyObject * p ) : m( p ) { Py_XINCREF( m ); } 106 PyRef(PyObject * p,__sal_NoAcquire)107 PyRef( PyObject * p, __sal_NoAcquire ) : m( p ) {} 108 PyRef(const PyRef & r)109 PyRef( const PyRef &r ) : m( r.get() ) { Py_XINCREF( m ); } 110 ~PyRef()111 ~PyRef() { Py_XDECREF( m ); } 112 get() const113 PyObject *get() const { return m; } 114 getAcquired() const115 PyObject * getAcquired() const 116 { 117 Py_XINCREF( const_cast< PyObject*> (m) ); 118 return m; 119 } 120 operator =(const PyRef & r)121 PyRef & operator = ( const PyRef & r ) 122 { 123 PyObject *tmp = m; 124 m = r.getAcquired(); 125 Py_XDECREF( tmp ); 126 return *this; 127 } 128 operator ==(const PyRef & r) const129 bool operator == ( const PyRef & r ) const 130 { 131 return r.get() == m; 132 } 133 134 /** clears the reference without decreasing the reference count 135 only seldomly needed ! */ scratch()136 void scratch() 137 { 138 m = 0; 139 } 140 141 /** clears the reference decreasing the refcount of the holded object. 142 */ clear()143 void clear() 144 { 145 Py_XDECREF( m ); 146 m = 0; 147 } 148 149 /** returns 1 when the reference points to a python object python object, 150 otherwise 0. 151 */ is() const152 sal_Bool is() const 153 { 154 return m != 0; 155 } 156 157 struct Hash 158 { operator ()pyuno::PyRef::Hash159 sal_IntPtr operator () ( const PyRef &r) const { return sal_IntPtr( r.get() ); } 160 }; 161 }; 162 163 struct stRuntimeImpl; 164 typedef struct stRuntimeImpl RuntimeImpl; 165 166 enum ConversionMode { ACCEPT_UNO_ANY, REJECT_UNO_ANY }; 167 168 169 /** The pyuno::Runtime class keeps the internal state of the python UNO bridge 170 for the currently in use python interpreter. 171 172 You may keep a Runtime instance, use it from a different thread, etc. But you must 173 make sure to fulfill all preconditions mentioned for the specific methods. 174 */ 175 176 class PY_DLLEXPORT Runtime 177 { 178 RuntimeImpl *impl; 179 public: 180 ~Runtime( ); 181 182 /** 183 preconditions: python has been initialized before, 184 the global interpreter lock is held and pyuno 185 has been initialized for the currently used interpreter. 186 187 Note: This method exists for efficiency reasons to save 188 lookup costs for any2PyObject and pyObject2Any 189 190 @throw RuntimeException in case the runtime has not been 191 initialized before 192 */ 193 Runtime() throw( com::sun::star::uno::RuntimeException ); 194 195 Runtime( const Runtime & ); 196 Runtime & operator = ( const Runtime & ); 197 198 /** Initializes the python-UNO bridge. May be called only once per python interpreter. 199 200 @param ctx the component context is used to instantiate bridge services needed 201 for bridging such as invocation, typeconverter, invocationadapterfactory, etc. 202 203 preconditions: python has been initialized before and 204 the global interpreter lock is held and pyuno is not 205 initialized (see isInitialized() ). 206 207 @throw RuntimeException in case the thread is not attached or the runtime 208 has not been initialized. 209 */ 210 static void SAL_CALL initialize( 211 const com::sun::star::uno::Reference< com::sun::star::uno::XComponentContext > & ctx ) 212 throw ( com::sun::star::uno::RuntimeException ); 213 214 215 /** Checks, whether the uno runtime is already initialized in the current python interpreter. 216 */ 217 static bool SAL_CALL isInitialized() throw (com::sun::star::uno::RuntimeException); 218 219 220 /** disposes the UNO bridge in this interpreter. All existing stubs/proxies 221 become non-functional, using these proxies/stubs leads to runtime errors. 222 223 preconditions: python has been initialized before and 224 the global interpreter lock is held and pyuno was 225 initialized before for the currently in use interpreter. 226 */ 227 static void SAL_CALL finalize() throw(com::sun::star::uno::RuntimeException ); 228 229 /** converts something contained in an UNO Any to a Python object 230 231 preconditions: python has been initialized before, 232 the global interpreter lock is held and pyuno::Runtime 233 has been initialized. 234 */ 235 PyRef any2PyObject (const com::sun::star::uno::Any &source ) const 236 throw ( com::sun::star::script::CannotConvertException, 237 com::sun::star::lang::IllegalArgumentException, 238 com::sun::star::uno::RuntimeException ); 239 240 /** converts a Python object to a UNO any 241 242 preconditions: python has been initialized before, 243 the global interpreter lock is held and pyuno 244 has been initialized 245 */ 246 com::sun::star::uno::Any pyObject2Any ( 247 const PyRef & source , enum ConversionMode mode = REJECT_UNO_ANY ) const 248 throw ( com::sun::star::uno::RuntimeException); 249 250 /** extracts a proper uno exception from a given python exception 251 */ 252 com::sun::star::uno::Any extractUnoException( 253 const PyRef & excType, const PyRef & excValue, const PyRef & excTraceback) const; 254 255 /** Returns the internal handle. Should only be used by the module implementation 256 */ getImpl() const257 RuntimeImpl *getImpl() const { return impl; } 258 }; 259 260 261 /** helper class for attaching the current thread to the python runtime. 262 263 Attaching is done creating a new threadstate for the given interpreter 264 and acquiring the global interpreter lock. 265 266 Usage: 267 268 ... don't use python here 269 { 270 PyThreadAttach guard( PyInterpreterState_Head() ); 271 { 272 ... do whatever python code you want 273 { 274 PyThreadDetach antiguard; 275 ... don't use python here 276 } 277 ... do whatever python code you want 278 } 279 } 280 ... don't use python here 281 282 Note: The additional scope brackets after the PyThreadAttach are needed, 283 e.g. when you would leave them away, dtors of potential pyrefs 284 may be called after the thread has detached again. 285 */ 286 class PY_DLLEXPORT PyThreadAttach 287 { 288 PyThreadState *tstate; 289 PyThreadAttach ( const PyThreadAttach & ); // not implemented 290 PyThreadAttach & operator = ( const PyThreadAttach & ); 291 public: 292 293 /** Creates a new python threadstate and acquires the global interpreter lock. 294 precondition: The current thread MUST NOT hold the global interpreter lock. 295 postcondition: The global interpreter lock is acquired 296 297 @raises com::sun::star::uno::RuntimeException 298 in case no pythread state could be created 299 */ 300 PyThreadAttach( PyInterpreterState *interp) throw ( com::sun::star::uno::RuntimeException ); 301 302 303 /** Releases the global interpreter lock and destroys the thread state. 304 */ 305 ~PyThreadAttach(); 306 }; 307 308 /** helper class for detaching the current thread from the python runtime 309 to do some blocking, non-python related operation. 310 311 @see PyThreadAttach 312 */ 313 class PY_DLLEXPORT PyThreadDetach 314 { 315 PyThreadState *tstate; 316 PyThreadDetach ( const PyThreadDetach & ); // not implemented 317 PyThreadDetach & operator = ( const PyThreadDetach & ); // not implemented 318 319 public: 320 /** Releases the global interpreter lock. 321 322 precondition: The current thread MUST hold the global interpreter lock. 323 postcondition: The current thread does not hold the global interpreter lock anymore. 324 */ 325 PyThreadDetach() throw ( com::sun::star::uno::RuntimeException ); 326 /** Acquires the global interpreter lock again 327 */ 328 ~PyThreadDetach(); 329 }; 330 331 } 332 #endif 333