Files
libreoffice/pyuno/inc/pyuno.hxx
Stephan Bergmann e57ca02849 Remove dynamic exception specifications
...(for now, from LIBO_INTERNAL_CODE only).  See the mail thread starting at
<https://lists.freedesktop.org/archives/libreoffice/2017-January/076665.html>
"Dynamic Exception Specifications" for details.

Most changes have been done automatically by the rewriting loplugin:dynexcspec
(after enabling the rewriting mode, to be committed shortly).  The way it only
removes exception specs from declarations if it also sees a definition, it
identified some dead declarations-w/o-definitions (that have been removed
manually) and some cases where a definition appeared in multiple include files
(which have also been cleaned up manually).  There's also been cases of macro
paramters (that were used to abstract over exception specs) that have become
unused now (and been removed).

Furthermore, some code needed to be cleaned up manually
(avmedia/source/quicktime/ and connectivity/source/drivers/kab/), as I had no
configurations available that would actually build that code.  Missing @throws
documentation has not been applied in such manual clean-up.

Change-Id: I3408691256c9b0c12bc5332de976743626e13960
Reviewed-on: https://gerrit.libreoffice.org/33574
Tested-by: Jenkins <ci@libreoffice.org>
Reviewed-by: Stephan Bergmann <sbergman@redhat.com>
2017-01-26 12:54:43 +00:00

332 lines
9.4 KiB
C++

/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This file incorporates work covered by the following license notice:
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed
* with this work for additional information regarding copyright
* ownership. The ASF licenses this file to you under the Apache
* License, Version 2.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.apache.org/licenses/LICENSE-2.0 .
*/
#ifndef INCLUDED_PYUNO_INC_PYUNO_HXX
#define INCLUDED_PYUNO_INC_PYUNO_HXX
#ifndef Py_PYTHON_H
#if defined _MSC_VER
#pragma warning(push, 1)
#endif
#include <Python.h>
#if defined _MSC_VER
#pragma warning(pop)
#endif
#endif // #ifdef Py_PYTHON_H
#include <com/sun/star/uno/XComponentContext.hpp>
#include <com/sun/star/script/CannotConvertException.hpp>
#include <com/sun/star/lang/IllegalArgumentException.hpp>
/**
External interface of the Python UNO bridge.
This is a C++ interface, because the core UNO components
invocation and proxyfactory are used to implement the bridge.
This interface is somewhat private and my change in future.
A scripting framework implementation may use this interface
to do the necessary conversions.
*/
#if defined LO_DLLIMPLEMENTATION_PYUNO
#define LO_DLLPUBLIC_PYUNO SAL_DLLPUBLIC_EXPORT
#else
#define LO_DLLPUBLIC_PYUNO SAL_DLLPUBLIC_IMPORT
#endif
/** function called by the python runtime to initialize the
pyuno module.
preconditions: python has been initialized before and
the global interpreter lock is held
*/
extern "C" LO_DLLPUBLIC_PYUNO
#if PY_MAJOR_VERSION >= 3
PyObject* SAL_CALL PyInit_pyuno();
#else
void SAL_CALL initpyuno();
#endif
namespace pyuno
{
enum NotNull
{
/** definition of a no acquire enum for ctors
*/
NOT_NULL
};
/** Helper class for keeping references to python objects.
BEWARE: Look up every python function you use to check
whether you get an acquired or not acquired object pointer
(python terminus for a not acquired object pointer
is 'borrowed reference'). Use in the acquired pointer cases the
PyRef( pointer, SAL_NO_ACQUIRE) ctor.
precondition: python has been initialized before and
the global interpreter lock is held
*/
class PyRef
{
PyObject *m;
public:
PyRef () : m(nullptr) {}
PyRef( PyObject * p ) : m( p ) { Py_XINCREF( m ); }
PyRef( PyObject * p, __sal_NoAcquire ) : m( p ) {}
PyRef( PyObject * p, __sal_NoAcquire, NotNull ) : m( p )
{
if (!m)
throw std::bad_alloc();
}
PyRef(const PyRef &r) : m(r.get()) { Py_XINCREF(m); }
PyRef(PyRef &&r) : m(r.get()) { r.scratch(); }
~PyRef() { Py_XDECREF( m ); }
PyObject *get() const { return m; }
PyObject * getAcquired() const
{
Py_XINCREF( m );
return m;
}
PyRef& operator=(const PyRef& r)
{
PyObject *tmp = m;
m = r.getAcquired();
Py_XDECREF(tmp);
return *this;
}
PyRef& operator=(PyRef&& r)
{
PyObject *tmp = m;
m = r.get();
r.scratch();
Py_XDECREF(tmp);
return *this;
}
bool operator == ( const PyRef & r ) const
{
return r.get() == m;
}
/** clears the reference without decreasing the reference count
only seldom needed ! */
void scratch()
{
m = nullptr;
}
/** returns 1 when the reference points to a python object python object,
otherwise 0.
*/
bool is() const
{
return m != nullptr;
}
struct Hash
{
sal_IntPtr operator () ( const PyRef &r) const { return sal_IntPtr( r.get() ); }
};
};
struct stRuntimeImpl;
typedef struct stRuntimeImpl RuntimeImpl;
enum ConversionMode { ACCEPT_UNO_ANY, REJECT_UNO_ANY };
/** The pyuno::Runtime class keeps the internal state of the python UNO bridge
for the currently in use python interpreter.
You may keep a Runtime instance, use it from a different thread, etc. But you must
make sure to fulfill all preconditions mentioned for the specific methods.
*/
class LO_DLLPUBLIC_PYUNO Runtime
{
RuntimeImpl *impl;
/**
Safely unpacks a Python iterator into a sequence, then
stores it in an Any. Used internally by pyObject2Any
*/
bool pyIterUnpack( PyObject *const, css::uno::Any & ) const;
public:
~Runtime( );
/**
preconditions: python has been initialized before,
the global interpreter lock is held and pyuno
has been initialized for the currently used interpreter.
Note: This method exists for efficiency reasons to save
lookup costs for any2PyObject and pyObject2Any
@throw RuntimeException in case the runtime has not been
initialized before
*/
Runtime();
Runtime( const Runtime & );
Runtime & operator = ( const Runtime & );
/** Initializes the python-UNO bridge. May be called only once per python interpreter.
@param ctx the component context is used to instantiate bridge services needed
for bridging such as invocation, typeconverter, invocationadapterfactory, etc.
preconditions: python has been initialized before and
the global interpreter lock is held and pyuno is not
initialized (see isInitialized() ).
@throw RuntimeException in case the thread is not attached or the runtime
has not been initialized.
*/
static void SAL_CALL initialize(
const css::uno::Reference< css::uno::XComponentContext > & ctx );
/** Checks, whether the uno runtime is already initialized in the current python interpreter.
@throws css::uno::RuntimeException
*/
static bool SAL_CALL isInitialized();
/** converts something contained in an UNO Any to a Python object
preconditions: python has been initialized before,
the global interpreter lock is held and pyuno::Runtime
has been initialized.
@throws css::script::CannotConvertException
@throws css::lang::IllegalArgumentException
@throws css::uno::RuntimeException
*/
PyRef any2PyObject (const css::uno::Any &source ) const;
/** converts a Python object to a UNO any
preconditions: python has been initialized before,
the global interpreter lock is held and pyuno
has been initialized
@throws css::uno::RuntimeException
*/
css::uno::Any pyObject2Any (
const PyRef & source , enum ConversionMode mode = REJECT_UNO_ANY ) const;
/** extracts a proper uno exception from a given python exception
*/
css::uno::Any extractUnoException(
const PyRef & excType, const PyRef & excValue, const PyRef & excTraceback) const;
/** Returns the internal handle. Should only be used by the module implementation
*/
RuntimeImpl *getImpl() const { return impl; }
};
/** helper class for attaching the current thread to the python runtime.
Attaching is done creating a new threadstate for the given interpreter
and acquiring the global interpreter lock.
Usage:
... don't use python here
{
PyThreadAttach guard( PyInterpreterState_Head() );
{
... do whatever python code you want
{
PyThreadDetach antiguard;
... don't use python here
}
... do whatever python code you want
}
}
... don't use python here
Note: The additional scope brackets after the PyThreadAttach are needed,
e.g. when you would leave them away, dtors of potential pyrefs
may be called after the thread has detached again.
*/
class LO_DLLPUBLIC_PYUNO PyThreadAttach
{
PyThreadState *tstate;
PyThreadAttach ( const PyThreadAttach & ) = delete;
PyThreadAttach & operator = ( const PyThreadAttach & ) = delete;
public:
/** Creates a new python threadstate and acquires the global interpreter lock.
precondition: The current thread MUST NOT hold the global interpreter lock.
postcondition: The global interpreter lock is acquired
@throws css::uno::RuntimeException
in case no pythread state could be created
*/
PyThreadAttach( PyInterpreterState *interp);
/** Releases the global interpreter lock and destroys the thread state.
*/
~PyThreadAttach();
};
/** helper class for detaching the current thread from the python runtime
to do some blocking, non-python related operation.
@see PyThreadAttach
*/
class LO_DLLPUBLIC_PYUNO PyThreadDetach
{
PyThreadState *tstate;
PyThreadDetach ( const PyThreadDetach & ) = delete;
PyThreadDetach & operator = ( const PyThreadDetach & ) = delete;
public:
/** Releases the global interpreter lock.
precondition: The current thread MUST hold the global interpreter lock.
postcondition: The current thread does not hold the global interpreter lock anymore.
@throws css::uno::RuntimeException
*/
PyThreadDetach();
/** Acquires the global interpreter lock again
*/
~PyThreadDetach();
};
}
#endif
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */