diff --git a/132.patch b/132.patch new file mode 100644 index 0000000..54843a5 --- /dev/null +++ b/132.patch @@ -0,0 +1,183 @@ +From 8d998cb79ebea348a8f5258b642a1f772ecd93b8 Mon Sep 17 00:00:00 2001 +From: Victor Stinner +Date: Tue, 3 Jul 2018 16:01:37 +0200 +Subject: [PATCH] Fix #131: Port to Py3.7: handle tstate->exc_info + +Fix Python 3.7 support: handle also tstate->exc_info, not only +tstate->exc_state. +--- + greenlet.c | 64 ++++++++++++++++++++++++++++++++++++++++++++++++-------------- + greenlet.h | 9 +++++++++ + 2 files changed, 59 insertions(+), 14 deletions(-) + +diff --git a/greenlet.c b/greenlet.c +index 0c85dd8..541efda 100644 +--- a/greenlet.c ++++ b/greenlet.c +@@ -153,6 +153,21 @@ static PyObject* ts_empty_dict; + #define GREENLET_tp_is_gc 0 + #endif /* !GREENLET_USE_GC */ + ++static void green_clear_exc(PyGreenlet *g) ++{ ++#ifdef GREENLET_USE_EXC_INFO ++ g->exc_info = NULL; ++ g->exc_state.exc_type = NULL; ++ g->exc_state.exc_value = NULL; ++ g->exc_state.exc_traceback = NULL; ++ g->exc_state.previous_item = NULL; ++#else ++ g->exc_type = NULL; ++ g->exc_value = NULL; ++ g->exc_traceback = NULL; ++#endif ++} ++ + static PyGreenlet* green_create_main(void) + { + PyGreenlet* gmain; +@@ -460,10 +475,9 @@ static int g_switchstack(void) + PyThreadState* tstate = PyThreadState_GET(); + current->recursion_depth = tstate->recursion_depth; + current->top_frame = tstate->frame; +-#if PY_VERSION_HEX >= 0x030700A3 +- current->exc_type = tstate->exc_state.exc_type; +- current->exc_value = tstate->exc_state.exc_value; +- current->exc_traceback = tstate->exc_state.exc_traceback; ++#ifdef GREENLET_USE_EXC_INFO ++ current->exc_info = tstate->exc_info; ++ current->exc_state = tstate->exc_state; + #else + current->exc_type = tstate->exc_type; + current->exc_value = tstate->exc_value; +@@ -474,9 +488,13 @@ static int g_switchstack(void) + if (err < 0) { /* error */ + PyGreenlet* current = ts_current; + current->top_frame = NULL; ++#ifdef GREENLET_USE_EXC_INFO ++ green_clear_exc(current); ++#else + current->exc_type = NULL; + current->exc_value = NULL; + current->exc_traceback = NULL; ++#endif + + assert(ts_origin == NULL); + ts_target = NULL; +@@ -488,18 +506,20 @@ static int g_switchstack(void) + tstate->recursion_depth = target->recursion_depth; + tstate->frame = target->top_frame; + target->top_frame = NULL; +-#if PY_VERSION_HEX >= 0x030700A3 +- tstate->exc_state.exc_type = target->exc_type; +- tstate->exc_state.exc_value = target->exc_value; +- tstate->exc_state.exc_traceback = target->exc_traceback; ++#ifdef GREENLET_USE_EXC_INFO ++ tstate->exc_state = target->exc_state; ++ if (target->exc_info != NULL) { ++ tstate->exc_info = target->exc_info; ++ } ++ else { ++ tstate->exc_info = &tstate->exc_state; ++ } + #else + tstate->exc_type = target->exc_type; + tstate->exc_value = target->exc_value; + tstate->exc_traceback = target->exc_traceback; + #endif +- target->exc_type = NULL; +- target->exc_value = NULL; +- target->exc_traceback = NULL; ++ green_clear_exc(target); + + assert(ts_origin == NULL); + Py_INCREF(target); +@@ -752,9 +772,7 @@ static int GREENLET_NOINLINE(g_initialstub)(void* mark) + self->stack_prev = ts_current; + } + self->top_frame = NULL; +- self->exc_type = NULL; +- self->exc_value = NULL; +- self->exc_traceback = NULL; ++ green_clear_exc(self); + self->recursion_depth = PyThreadState_GET()->recursion_depth; + + /* restore arguments in case they are clobbered */ +@@ -935,9 +953,15 @@ green_traverse(PyGreenlet *self, visitproc visit, void *arg) + - frames are not visited: alive greenlets are not garbage collected anyway */ + Py_VISIT((PyObject*)self->parent); + Py_VISIT(self->run_info); ++#ifdef GREENLET_USE_EXC_INFO ++ Py_VISIT(self->exc_state.exc_type); ++ Py_VISIT(self->exc_state.exc_value); ++ Py_VISIT(self->exc_state.exc_traceback); ++#else + Py_VISIT(self->exc_type); + Py_VISIT(self->exc_value); + Py_VISIT(self->exc_traceback); ++#endif + Py_VISIT(self->dict); + return 0; + } +@@ -961,9 +985,15 @@ static int green_clear(PyGreenlet* self) + so even if it switches we are relatively safe. */ + Py_CLEAR(self->parent); + Py_CLEAR(self->run_info); ++#ifdef GREENLET_USE_EXC_INFO ++ Py_CLEAR(self->exc_state.exc_type); ++ Py_CLEAR(self->exc_state.exc_value); ++ Py_CLEAR(self->exc_state.exc_traceback); ++#else + Py_CLEAR(self->exc_type); + Py_CLEAR(self->exc_value); + Py_CLEAR(self->exc_traceback); ++#endif + Py_CLEAR(self->dict); + return 0; + } +@@ -1030,9 +1060,15 @@ static void green_dealloc(PyGreenlet* self) + PyObject_ClearWeakRefs((PyObject *) self); + Py_CLEAR(self->parent); + Py_CLEAR(self->run_info); ++#ifdef GREENLET_USE_EXC_INFO ++ Py_CLEAR(self->exc_state.exc_type); ++ Py_CLEAR(self->exc_state.exc_value); ++ Py_CLEAR(self->exc_state.exc_traceback); ++#else + Py_CLEAR(self->exc_type); + Py_CLEAR(self->exc_value); + Py_CLEAR(self->exc_traceback); ++#endif + Py_CLEAR(self->dict); + Py_TYPE(self)->tp_free((PyObject*) self); + } +diff --git a/greenlet.h b/greenlet.h +index 6c9b8ee..995f500 100644 +--- a/greenlet.h ++++ b/greenlet.h +@@ -13,6 +13,10 @@ extern "C" { + + #define GREENLET_VERSION "0.4.13" + ++#if PY_VERSION_HEX >= 0x030700A3 ++# define GREENLET_USE_EXC_INFO ++#endif ++ + typedef struct _greenlet { + PyObject_HEAD + char* stack_start; +@@ -25,9 +29,14 @@ typedef struct _greenlet { + struct _frame* top_frame; + int recursion_depth; + PyObject* weakreflist; ++#ifdef GREENLET_USE_EXC_INFO ++ _PyErr_StackItem *exc_info; ++ _PyErr_StackItem exc_state; ++#else + PyObject* exc_type; + PyObject* exc_value; + PyObject* exc_traceback; ++#endif + PyObject* dict; + } PyGreenlet; + diff --git a/python-greenlet.spec b/python-greenlet.spec index 03bac3a..437fe21 100644 --- a/python-greenlet.spec +++ b/python-greenlet.spec @@ -2,7 +2,7 @@ Name: python-%{modname} Version: 0.4.13 -Release: 3%{?dist} +Release: 4%{?dist} Summary: Lightweight in-process concurrent programming License: MIT URL: https://github.com/python-greenlet/greenlet @@ -10,6 +10,9 @@ Source0: %{url}/archive/%{version}/%{modname}-%{version}.tar.gz # https://github.com/python-greenlet/greenlet/pull/120 Patch0001: 0001-Don-t-clobber-r2-register-on-ppc64el.patch +# https://bugzilla.redhat.com/show_bug.cgi?id=1594248 +Patch0002: https://github.com/python-greenlet/greenlet/pull/132.patch + %global _description \ The greenlet package is a spin-off of Stackless, a version of CPython\ that supports micro-threads called "tasklets". Tasklets run\ @@ -92,6 +95,9 @@ Python 3 version. %{_includedir}/python%{python3_version}*/%{modname}/ %changelog +* Tue Jul 03 2018 Miro Hrončok - 0.4.13-4 +- Add fix for Python 3.7 + * Sat Jun 16 2018 Miro Hrončok - 0.4.13-3 - Rebuilt for Python 3.7