Example #1
0
PyObject* PythonSecurity::compile_restricted(const QString& source, const QString& filename, const QString& mode)
{
    krossdebug("PythonSecurity::compile_restricted");
    if(! m_pymodule)
        initRestrictedPython(); // throws exception if failed

    try {
        Py::Dict mainmoduledict = ((PythonInterpreter*)m_interpreter)->mainModule()->getDict();

        PyObject* func = PyDict_GetItemString(m_pymodule->getDict().ptr(), "compile_restricted");
        if(! func)
            throw Kross::Api::Exception::Ptr( new Kross::Api::Exception(QString("No such function '%1'.").arg("compile_restricted")) );

        Py::Callable funcobject(func, true); // the funcobject takes care of freeing our func pyobject.

        if(! funcobject.isCallable())
            throw Kross::Api::Exception::Ptr( new Kross::Api::Exception(QString("Function '%1' is not callable.").arg("compile_restricted")) );

        Py::Tuple args(3);
        args[0] = Py::String(source.utf8());
        args[1] = Py::String(filename.utf8());
        args[2] = Py::String(mode.utf8());

        Py::Object result = funcobject.apply(args);

        PyObject* pycode = PyEval_EvalCode(
            (PyCodeObject*)result.ptr(),
            mainmoduledict.ptr(),
            mainmoduledict.ptr()
        );
        if(! pycode)
            throw Py::Exception();

        /*
        Py::List ml = mainmoduledict;
        for(Py::List::size_type mi = 0; mi < ml.length(); ++mi) {
            krossdebug( QString("dir() = %1").arg( ml[mi].str().as_string().c_str() ) );
            //krossdebug( QString("dir().dir() = %1").arg( Py::Object(ml[mi]).dir().as_string().c_str() ) );
        }
        */

        Py::Object code(pycode);
        krossdebug( QString("%1 callable=%2").arg(code.as_string().c_str()).arg(PyCallable_Check(code.ptr())) );
        Py::List l = code.dir();
        for(Py::List::size_type i = 0; i < l.length(); ++i) {
            krossdebug( QString("dir() = %1").arg( l[i].str().as_string().c_str() ) );
            //krossdebug( QString("dir().dir() = %1").arg( Py::Object(l[i]).dir().as_string().c_str() ) );
        }

        return pycode;
    }
    catch(Py::Exception& e) { 
        QString err = Py::value(e).as_string().c_str();
        e.clear();
        throw Kross::Api::Exception::Ptr( new Kross::Api::Exception(QString("Function '%1' failed with python exception: %2").arg("compile_restricted").arg(err) ) );
    }
}
Example #2
0
Py::List toListOfStrings( Py::Object obj )
{
    Py::List list;
    if( obj.isList() )
        list = obj;
    else
        list.append( obj );

    // check all members of the list are strings
    for( Py::List::size_type i=0; i<list.length(); i++ )
    {
        Py::String path_str( list[i] );
    }

    return list;
}
void PythonInterpreter::extractException(QStringList& errorlist, int& lineno)
{
    lineno = -1;

    PyObject *type, *value, *traceback;
    PyErr_Fetch(&type, &value, &traceback);
    Py_FlushLine();
    PyErr_NormalizeException(&type, &value, &traceback);
    if(traceback) {
        Py::List tblist;
        try {
            Py::Module tbmodule( PyImport_Import(Py::String("traceback").ptr()), true );
            Py::Dict tbdict = tbmodule.getDict();
            Py::Callable tbfunc(tbdict.getItem("format_tb"));
            Py::Tuple args(1);
            args.setItem(0, Py::Object(traceback));
            tblist = tbfunc.apply(args);
            uint length = tblist.length();
            for(Py::List::size_type i = 0; i < length; ++i)
                errorlist.append( Py::Object(tblist[i]).as_string().c_str() );
        }
        catch(Py::Exception& e) {
            QString err = Py::value(e).as_string().c_str();
            e.clear(); // exception is handled. clear it now.
            #ifdef KROSS_PYTHON_EXCEPTION_DEBUG
                krosswarning( QString("Kross::PythonScript::toException() Failed to fetch a traceback: %1").arg(err) );
            #endif
        }

        PyObject *next;
        while (traceback && traceback != Py_None) {
            PyFrameObject *frame = (PyFrameObject*)PyObject_GetAttrString(traceback, const_cast< char* >("tb_frame"));
            {
                PyObject *getobj = PyObject_GetAttrString(traceback, const_cast< char* >("tb_lineno") );
                lineno = PyInt_AsLong(getobj);
                Py_DECREF(getobj);
            }
            if(Py_OptimizeFlag) {
                PyObject *getobj = PyObject_GetAttrString(traceback, const_cast< char* >("tb_lasti") );
                int lasti = PyInt_AsLong(getobj);
                Py_DECREF(getobj);
                lineno = PyCode_Addr2Line(frame->f_code, lasti);
            }

            //const char* filename = PyString_AsString(frame->f_code->co_filename);
            //const char* name = PyString_AsString(frame->f_code->co_name);
            //errorlist.append( QString("%1#%2: \"%3\"").arg(filename).arg(lineno).arg(name) );

            //Py_DECREF(frame); // don't free cause we don't own it.

            next = PyObject_GetAttrString(traceback, const_cast< char* >("tb_next") );
            Py_DECREF(traceback);
            traceback = next;
        }
    }

    if(lineno < 0 && value && PyObject_HasAttrString(value, const_cast< char* >("lineno"))) {
        PyObject *getobj = PyObject_GetAttrString(value, const_cast< char* >("lineno") );
        if(getobj) {
            lineno = PyInt_AsLong(getobj);
            Py_DECREF(getobj);
        }
    }

    #ifdef KROSS_PYTHON_EXCEPTION_DEBUG
        //krossdebug( QString("PythonInterpreter::extractException: %1").arg( Py::Object(value).as_string().c_str() ) );
        krossdebug( QString("PythonInterpreter::extractException:\n%1").arg( errorlist.join("\n") ) );
    #endif
    PyErr_Restore(type, value, traceback);
}