[prev in list] [next in list] [prev in thread] [next in thread]
List: gcc-python-plugin-commits
Subject: [gcc-python-plugin] track which event we're within when a callback fires
From: dmalcolm () fedoraproject ! org (dmalcolm)
Date: 2011-10-25 19:55:03
Message-ID: 20111025195503.CF5E412020B () lists ! fedorahosted ! org
[Download RAW message or body]
commit 2143f3f09a10f522a506ec6792f7bc7d0aab3e50
Author: David Malcolm <dmalcolm at redhat.com>
Date: Tue Oct 25 15:49:51 2011 -0400
track which event we're within when a callback fires
This will be of use when bulletproofing certain APIs that can only
be called at certain times within the compilation.
gcc-python-closure.c | 15 ++++++++++++++-
gcc-python-closure.h | 12 +++++++++++-
gcc-python-gimple.c | 2 +-
gcc-python.c | 25 ++++++++++++++++++++++++-
gcc-python.h | 5 +++++
5 files changed, 55 insertions(+), 4 deletions(-)
---
diff --git a/gcc-python-closure.c b/gcc-python-closure.c
index c6f83dc..5c9b8ae 100644
--- a/gcc-python-closure.c
+++ b/gcc-python-closure.c
@@ -25,7 +25,7 @@
#include "function.h"
struct callback_closure *
-gcc_python_closure_new(PyObject *callback, PyObject *extraargs, PyObject *kwargs)
+gcc_python_closure_new_generic(PyObject *callback, PyObject *extraargs, PyObject *kwargs)
{
struct callback_closure *closure;
@@ -59,6 +59,19 @@ gcc_python_closure_new(PyObject *callback, PyObject *extraargs, PyObject *kwargs
Py_INCREF(kwargs);
}
+ closure->event = GCC_PYTHON_PLUGIN_BAD_EVENT;
+
+ return closure;
+}
+
+struct callback_closure *
+gcc_python_closure_new_for_plugin_event(PyObject *callback, PyObject *extraargs, PyObject *kwargs,
+ enum plugin_event event)
+{
+ struct callback_closure *closure = gcc_python_closure_new_generic(callback, extraargs, kwargs);
+ if (closure) {
+ closure->event = event;
+ }
return closure;
}
diff --git a/gcc-python-closure.h b/gcc-python-closure.h
index 99dc170..7950fbc 100644
--- a/gcc-python-closure.h
+++ b/gcc-python-closure.h
@@ -25,10 +25,20 @@ struct callback_closure
PyObject *callback;
PyObject *extraargs;
PyObject *kwargs;
+ enum plugin_event event;
+ /* or GCC_PYTHON_PLUGIN_BAD_EVENT if not an event */
};
struct callback_closure *
-gcc_python_closure_new(PyObject *callback, PyObject *extraargs, PyObject *kwargs);
+gcc_python_closure_new_generic(PyObject *callback,
+ PyObject *extraargs,
+ PyObject *kwargs);
+
+struct callback_closure *
+gcc_python_closure_new_for_plugin_event(PyObject *callback,
+ PyObject *extraargs,
+ PyObject *kwargs,
+ enum plugin_event event);
PyObject *
gcc_python_closure_make_args(struct callback_closure * closure,
diff --git a/gcc-python-gimple.c b/gcc-python-gimple.c
index 7baec2b..8e24408 100644
--- a/gcc-python-gimple.c
+++ b/gcc-python-gimple.c
@@ -119,7 +119,7 @@ gcc_Gimple_walk_tree(struct PyGccGimple * self, PyObject *args, PyObject *kwargs
callback = PyTuple_GetItem(args, 0);
extraargs = PyTuple_GetSlice(args, 1, PyTuple_Size(args));
- closure = gcc_python_closure_new(callback, extraargs, kwargs);
+ closure = gcc_python_closure_new_generic(callback, extraargs, kwargs);
if (!closure) {
return NULL;
}
diff --git a/gcc-python.c b/gcc-python.c
index 30a6a17..544415f 100644
--- a/gcc-python.c
+++ b/gcc-python.c
@@ -149,6 +149,21 @@ static void trace_callback_for_##NAME(void *gcc_data, void *user_data) \
# undef DEFEVENT
#endif /* GCC_PYTHON_TRACE_ALL_EVENTS */
+static enum plugin_event current_event = GCC_PYTHON_PLUGIN_BAD_EVENT;
+
+int gcc_python_is_within_event(enum plugin_event *out_event)
+{
+ if (current_event != GCC_PYTHON_PLUGIN_BAD_EVENT) {
+ if (out_event) {
+ *out_event = current_event;
+ }
+ return 1;
+ } else {
+ return 0;
+ }
+}
+
+
static void
gcc_python_finish_invoking_callback(PyGILState_STATE gstate,
int expect_wrapped_data, PyObject *wrapped_gcc_data,
@@ -158,6 +173,7 @@ gcc_python_finish_invoking_callback(PyGILState_STATE gstate,
PyObject *args = NULL;
PyObject *result = NULL;
location_t saved_loc = input_location;
+ enum plugin_event saved_event;
assert(closure);
/* We take ownership of wrapped_gcc_data.
@@ -176,8 +192,14 @@ gcc_python_finish_invoking_callback(PyGILState_STATE gstate,
if (!args) {
goto cleanup;
}
+
+ saved_event = current_event;
+ current_event = closure->event;
+
result = PyObject_Call(closure->callback, args, closure->kwargs);
+ current_event = saved_event;
+
if (!result) {
/* Treat an unhandled Python error as a compilation error: */
gcc_python_print_exception("Unhandled Python exception raised within callback");
@@ -277,7 +299,8 @@ gcc_python_register_callback(PyObject *self, PyObject *args, PyObject *kwargs)
//printf("%s:%i:gcc_python_register_callback\n", __FILE__, __LINE__);
- closure = gcc_python_closure_new(callback, extraargs, kwargs);
+ closure = gcc_python_closure_new_for_plugin_event(callback, extraargs, kwargs,
+ (enum plugin_event)event);
if (!closure) {
return PyErr_NoMemory();
}
diff --git a/gcc-python.h b/gcc-python.h
index f350ea7..55af6fa 100644
--- a/gcc-python.h
+++ b/gcc-python.h
@@ -25,6 +25,9 @@
#include "gimple.h"
#include "params.h"
+/* GCC doesn't seem to give us an ID for "invalid event", so invent one: */
+#define GCC_PYTHON_PLUGIN_BAD_EVENT (0xffff)
+
/*
Macro DECLARE_SIMPLE_WRAPPER():
ARG_structname:
@@ -217,6 +220,8 @@ gcc_python_insert_new_wrapper_into_cache(PyObject **cache,
/* gcc-python.c */
+int gcc_python_is_within_event(enum plugin_event *out_event);
+
char * gcc_python_strdup(const char *str);
void gcc_python_print_exception(const char *msg);
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic