/* * Copyright (C) 2013-2018 Team Kodi * This file is part of Kodi - https://kodi.tv * * SPDX-License-Identifier: GPL-2.0-or-later * See LICENSES/README.md for more information. */ #pragma once #include "interfaces/generic/ILanguageInvoker.h" #include "interfaces/legacy/Addon.h" #include "interfaces/python/LanguageHook.h" #include "threads/CriticalSection.h" #include "threads/Event.h" #include #include #include typedef struct _object PyObject; class CPythonInvoker : public ILanguageInvoker { public: explicit CPythonInvoker(ILanguageInvocationHandler* invocationHandler); ~CPythonInvoker() override; bool Execute(const std::string& script, const std::vector& arguments = std::vector()) override; bool IsStopping() const override { return m_stop || ILanguageInvoker::IsStopping(); } typedef PyObject* (*PythonModuleInitialization)(); protected: // implementation of ILanguageInvoker bool execute(const std::string& script, const std::vector& arguments) override; virtual void executeScript(FILE* fp, const std::string& script, PyObject* moduleDict); bool stop(bool abort) override; void onExecutionDone() override; void onExecutionFailed() override; // custom virtual methods virtual std::map getModules() const = 0; virtual const char* getInitializationScript() const = 0; virtual void onInitialization(); // actually a PyObject* but don't wanna draw Python.h include into the header virtual void onPythonModuleInitialization(void* moduleDict); virtual void onDeinitialization(); virtual void onSuccess() {} virtual void onAbort() {} virtual void onError(const std::string& exceptionType = "", const std::string& exceptionValue = "", const std::string& exceptionTraceback = ""); std::string m_sourceFile; CCriticalSection m_critical; private: void initializeModules(const std::map& modules); bool initializeModule(PythonModuleInitialization module); void getAddonModuleDeps(const ADDON::AddonPtr& addon, std::set& paths); bool execute(const std::string& script, std::vector& arguments); FILE* PyFile_AsFileWithMode(PyObject* py_file, const char* mode); PyThreadState* m_threadState; bool m_stop; CEvent m_stoppedEvent; XBMCAddon::AddonClass::Ref m_languageHook; bool m_systemExitThrown = false; static CCriticalSection s_critical; };