PageRenderTime 52ms CodeModel.GetById 13ms app.highlight 32ms RepoModel.GetById 2ms app.codeStats 0ms

/Modules/_llvm.c

http://unladen-swallow.googlecode.com/
C | 207 lines | 171 code | 27 blank | 9 comment | 28 complexity | d971897c3e0df1b18e5a3d3d4c2a6e3f MD5 | raw file
  1/* _llvm module */
  2
  3/*
  4This module provides a way to get at the minimal LLVM wrapper
  5types. It's not intended to be a full LLVM interface. For that, use
  6LLVM-py.
  7*/
  8
  9#include "Python.h"
 10#include "_llvmfunctionobject.h"
 11#include "JIT/global_llvm_data_fwd.h"
 12#include "JIT/llvm_compile.h"
 13#include "JIT/RuntimeFeedback_fwd.h"
 14
 15PyDoc_STRVAR(llvm_module_doc,
 16"Defines thin wrappers around fundamental LLVM types.");
 17
 18PyDoc_STRVAR(setdebug_doc,
 19             "set_debug(bool).  Sets LLVM debug output on or off.");
 20static PyObject *
 21llvm_setdebug(PyObject *self, PyObject *on_obj)
 22{
 23    int on = PyObject_IsTrue(on_obj);
 24    if (on == -1)  /* Error. */
 25        return NULL;
 26
 27    if (!PyLlvm_SetDebug(on)) {
 28        PyErr_SetString(PyExc_ValueError, "llvm debugging not available");
 29        return NULL;
 30    }
 31    Py_RETURN_NONE;
 32}
 33
 34PyDoc_STRVAR(llvm_compile_doc,
 35"compile(code, optimization_level) -> llvm_function\n\
 36\n\
 37Compile a code object to an llvm_function object at the given\n\
 38optimization level.");
 39
 40static PyObject *
 41llvm_compile(PyObject *self, PyObject *args)
 42{
 43    PyObject *obj;
 44    PyCodeObject *code;
 45    long opt_level;
 46
 47    if (!PyArg_ParseTuple(args, "O!l:compile",
 48                          &PyCode_Type, &obj, &opt_level))
 49        return NULL;
 50
 51    if (opt_level < -1 || opt_level > Py_MAX_LLVM_OPT_LEVEL) {
 52        PyErr_SetString(PyExc_ValueError, "invalid optimization level");
 53        return NULL;
 54    }
 55
 56    code = (PyCodeObject *)obj;
 57    if (code->co_llvm_function)
 58        _LlvmFunction_Dealloc(code->co_llvm_function);
 59    code->co_llvm_function = _PyCode_ToLlvmIr(code);
 60    if (code->co_llvm_function == NULL)
 61        return NULL;
 62    if (code->co_optimization < opt_level &&
 63        PyGlobalLlvmData_Optimize(PyGlobalLlvmData_GET(),
 64                                  code->co_llvm_function, opt_level) < 0) {
 65        PyErr_Format(PyExc_ValueError,
 66                     "Failed to optimize to level %ld", opt_level);
 67        _LlvmFunction_Dealloc(code->co_llvm_function);
 68        return NULL;
 69    }
 70
 71    return _PyLlvmFunction_FromCodeObject((PyObject *)code);
 72}
 73
 74PyDoc_STRVAR(llvm_clear_feedback_doc,
 75"clear_feedback(func)\n\
 76\n\
 77Clear the runtime feedback collected for the given function.");
 78
 79static PyObject *
 80llvm_clear_feedback(PyObject *self, PyObject *obj)
 81{
 82    PyCodeObject *code;
 83    if (PyFunction_Check(obj)) {
 84        PyFunctionObject *func = (PyFunctionObject *)obj;
 85        code = (PyCodeObject *)func->func_code;
 86    }
 87    else if (PyMethod_Check(obj)) {
 88        /* Methods contain other callable objects, including, potentially other
 89           methods. */
 90        return llvm_clear_feedback(self, ((PyMethodObject *)obj)->im_func);
 91    }
 92    else if (PyCode_Check(obj)) {
 93        code = (PyCodeObject *)obj;
 94    }
 95    else if (PyCFunction_Check(obj)) {  /* No feedback; this is a no-op. */
 96        Py_RETURN_NONE;
 97    }
 98    else {
 99        PyErr_Format(PyExc_TypeError,
100                     "cannot clear feedback for %.100s objects",
101                     Py_TYPE(obj)->tp_name);
102        return NULL;
103    }
104
105    if (code->co_runtime_feedback)
106        PyFeedbackMap_Clear(code->co_runtime_feedback);
107    Py_RETURN_NONE;
108}
109
110PyDoc_STRVAR(llvm_set_jit_control_doc,
111"set_jit_control(string)\n\
112\n\
113Set the JIT control mode.  Valid values are 'always', 'never', and 'whenhot'.");
114
115static PyObject *
116llvm_set_jit_control(PyObject *self, PyObject *flag_obj)
117{
118    const char *flag_str;
119    if (!PyString_Check(flag_obj)) {
120        PyErr_Format(PyExc_TypeError,
121                     "expected str, not %.100s object",
122                     Py_TYPE(flag_obj)->tp_name);
123        return NULL;
124    }
125
126    flag_str = PyString_AsString(flag_obj);
127    if (flag_str == NULL)
128        return NULL;
129    if (Py_JitControlStrToEnum(flag_str, &Py_JitControl) < 0) {
130        PyErr_Format(PyExc_ValueError,
131                     "invalid jit control value: \"%s\"", flag_str);
132        return NULL;
133    }
134    Py_RETURN_NONE;
135}
136
137PyDoc_STRVAR(llvm_get_jit_control_doc,
138"get_jit_control() -> string\n\
139\n\
140Returns the current value for the Py_JitControl flag.  This may disagree\n\
141with sys.flags.jit_control because the sys.flags structure is immutable and\n\
142it is initialized at load time, so it reflects the value passed to the\n\
143program on the command line.");
144
145static PyObject *
146llvm_get_jit_control(PyObject *self)
147{
148    const char *flag_str = Py_JitControlEnumToStr(Py_JitControl);
149    assert(flag_str != NULL && "Current JIT control value was invalid!");
150    return PyString_FromString(flag_str);
151}
152
153PyDoc_STRVAR(llvm_get_hotness_threshold_doc,
154"get_hotness_threshold() -> long\n\
155\n\
156Return the threshold for co_hotness before the code is 'hot'.");
157
158static PyObject *
159llvm_get_hotness_threshold(PyObject *self)
160{
161    return PyInt_FromLong(PY_HOTNESS_THRESHOLD);
162}
163
164PyDoc_STRVAR(llvm_collect_unused_globals_doc,
165"collect_unused_globals()\n\
166\n\
167Collect any unused LLVM global variables that may be holding references to\n\
168Python objects.");
169
170static PyObject *
171llvm_collect_unused_globals(PyObject *self)
172{
173    PyGlobalLlvmData_CollectUnusedGlobals(PyGlobalLlvmData_GET());
174    Py_RETURN_NONE;
175}
176
177static struct PyMethodDef llvm_methods[] = {
178    {"set_debug", (PyCFunction)llvm_setdebug, METH_O, setdebug_doc},
179    {"compile", llvm_compile, METH_VARARGS, llvm_compile_doc},
180    {"clear_feedback", (PyCFunction)llvm_clear_feedback, METH_O,
181     llvm_clear_feedback_doc},
182    {"get_jit_control", (PyCFunction)llvm_get_jit_control, METH_NOARGS,
183     llvm_get_jit_control_doc},
184    {"set_jit_control", (PyCFunction)llvm_set_jit_control, METH_O,
185     llvm_set_jit_control_doc},
186    {"get_hotness_threshold", (PyCFunction)llvm_get_hotness_threshold,
187     METH_NOARGS, llvm_get_hotness_threshold_doc},
188    {"collect_unused_globals", (PyCFunction)llvm_collect_unused_globals,
189     METH_NOARGS, llvm_collect_unused_globals_doc},
190    { NULL, NULL }
191};
192
193PyMODINIT_FUNC
194init_llvm(void)
195{
196    PyObject *module;
197
198    /* Create the module and add the functions */
199    module = Py_InitModule3("_llvm", llvm_methods, llvm_module_doc);
200    if (module == NULL)
201        return;
202
203    Py_INCREF(&PyLlvmFunction_Type);
204    if (PyModule_AddObject(module, "_function",
205                           (PyObject *)&PyLlvmFunction_Type))
206        return;
207}