|
69 | 69 |
|
70 | 70 | #define POSIX_CALL(call) do { if ((call) == -1) goto error; } while (0) |
71 | 71 |
|
72 | | -typedef struct { |
73 | | - PyObject* disable; |
74 | | - PyObject* enable; |
75 | | - PyObject* isenabled; |
76 | | -} _posixsubprocessstate; |
77 | | - |
78 | 72 | static struct PyModuleDef _posixsubprocessmodule; |
79 | 73 |
|
80 | | -static inline _posixsubprocessstate* |
81 | | -get_posixsubprocess_state(PyObject *module) |
82 | | -{ |
83 | | - void *state = PyModule_GetState(module); |
84 | | - assert(state != NULL); |
85 | | - return (_posixsubprocessstate *)state; |
86 | | -} |
87 | | - |
88 | | -/* If gc was disabled, call gc.enable(). Ignore errors. */ |
89 | | -static void |
90 | | -_enable_gc(int need_to_reenable_gc, PyObject *gc_module, _posixsubprocessstate *state) |
91 | | -{ |
92 | | - PyObject *result; |
93 | | - PyObject *exctype, *val, *tb; |
94 | | - |
95 | | - if (need_to_reenable_gc) { |
96 | | - PyErr_Fetch(&exctype, &val, &tb); |
97 | | - result = PyObject_CallMethodNoArgs( |
98 | | - gc_module, state->enable); |
99 | | - if (result == NULL) { |
100 | | - /* We might have created a child process at this point, we |
101 | | - * we have no good way to handle a failure to reenable GC |
102 | | - * and return information about the child process. */ |
103 | | - PyErr_Print(); |
104 | | - } |
105 | | - Py_XDECREF(result); |
106 | | - if (exctype != NULL) { |
107 | | - PyErr_Restore(exctype, val, tb); |
108 | | - } |
109 | | - } |
110 | | -} |
111 | | - |
112 | | - |
113 | 74 | /* Convert ASCII to a positive int, no libc call. no overflow. -1 on error. */ |
114 | 75 | static int |
115 | 76 | _pos_int_from_ascii(const char *name) |
@@ -780,7 +741,6 @@ subprocess_fork_exec(PyObject *module, PyObject *args) |
780 | 741 | Py_ssize_t arg_num, num_groups = 0; |
781 | 742 | int need_after_fork = 0; |
782 | 743 | int saved_errno = 0; |
783 | | - _posixsubprocessstate *state = get_posixsubprocess_state(module); |
784 | 744 |
|
785 | 745 | if (!PyArg_ParseTuple( |
786 | 746 | args, "OOpO!OOiiiiiiiiiiOOOiO:fork_exec", |
@@ -820,30 +780,7 @@ subprocess_fork_exec(PyObject *module, PyObject *args) |
820 | 780 |
|
821 | 781 | /* We need to call gc.disable() when we'll be calling preexec_fn */ |
822 | 782 | if (preexec_fn != Py_None) { |
823 | | - PyObject *result; |
824 | | - |
825 | | - gc_module = PyImport_ImportModule("gc"); |
826 | | - if (gc_module == NULL) |
827 | | - return NULL; |
828 | | - result = PyObject_CallMethodNoArgs( |
829 | | - gc_module, state->isenabled); |
830 | | - if (result == NULL) { |
831 | | - Py_DECREF(gc_module); |
832 | | - return NULL; |
833 | | - } |
834 | | - need_to_reenable_gc = PyObject_IsTrue(result); |
835 | | - Py_DECREF(result); |
836 | | - if (need_to_reenable_gc == -1) { |
837 | | - Py_DECREF(gc_module); |
838 | | - return NULL; |
839 | | - } |
840 | | - result = PyObject_CallMethodNoArgs( |
841 | | - gc_module, state->disable); |
842 | | - if (result == NULL) { |
843 | | - Py_DECREF(gc_module); |
844 | | - return NULL; |
845 | | - } |
846 | | - Py_DECREF(result); |
| 783 | + need_to_reenable_gc = PyGC_Disable(); |
847 | 784 | } |
848 | 785 |
|
849 | 786 | exec_array = _PySequence_BytesToCharpArray(executable_list); |
@@ -1068,7 +1005,9 @@ subprocess_fork_exec(PyObject *module, PyObject *args) |
1068 | 1005 | if (exec_array) |
1069 | 1006 | _Py_FreeCharPArray(exec_array); |
1070 | 1007 |
|
1071 | | - _enable_gc(need_to_reenable_gc, gc_module, state); |
| 1008 | + if (need_to_reenable_gc) { |
| 1009 | + PyGC_Enable(); |
| 1010 | + } |
1072 | 1011 | Py_XDECREF(gc_module); |
1073 | 1012 |
|
1074 | 1013 | return pid == -1 ? NULL : PyLong_FromPid(pid); |
@@ -1108,67 +1047,22 @@ Raises: Only on an error in the parent process.\n\ |
1108 | 1047 | PyDoc_STRVAR(module_doc, |
1109 | 1048 | "A POSIX helper for the subprocess module."); |
1110 | 1049 |
|
1111 | | -static int |
1112 | | -_posixsubprocess_exec(PyObject *module) |
1113 | | -{ |
1114 | | - _posixsubprocessstate *state = get_posixsubprocess_state(module); |
1115 | | - |
1116 | | - state->disable = PyUnicode_InternFromString("disable"); |
1117 | | - if (state->disable == NULL) { |
1118 | | - return -1; |
1119 | | - } |
1120 | | - |
1121 | | - state->enable = PyUnicode_InternFromString("enable"); |
1122 | | - if (state->enable == NULL) { |
1123 | | - return -1; |
1124 | | - } |
1125 | | - |
1126 | | - state->isenabled = PyUnicode_InternFromString("isenabled"); |
1127 | | - if (state->isenabled == NULL) { |
1128 | | - return -1; |
1129 | | - } |
1130 | | - |
1131 | | - return 0; |
1132 | | -} |
1133 | | - |
1134 | 1050 | static PyMethodDef module_methods[] = { |
1135 | 1051 | {"fork_exec", subprocess_fork_exec, METH_VARARGS, subprocess_fork_exec_doc}, |
1136 | 1052 | {NULL, NULL} /* sentinel */ |
1137 | 1053 | }; |
1138 | 1054 |
|
1139 | 1055 | static PyModuleDef_Slot _posixsubprocess_slots[] = { |
1140 | | - {Py_mod_exec, _posixsubprocess_exec}, |
1141 | 1056 | {0, NULL} |
1142 | 1057 | }; |
1143 | 1058 |
|
1144 | | -static int _posixsubprocess_traverse(PyObject *m, visitproc visit, void *arg) { |
1145 | | - Py_VISIT(get_posixsubprocess_state(m)->disable); |
1146 | | - Py_VISIT(get_posixsubprocess_state(m)->enable); |
1147 | | - Py_VISIT(get_posixsubprocess_state(m)->isenabled); |
1148 | | - return 0; |
1149 | | -} |
1150 | | - |
1151 | | -static int _posixsubprocess_clear(PyObject *m) { |
1152 | | - Py_CLEAR(get_posixsubprocess_state(m)->disable); |
1153 | | - Py_CLEAR(get_posixsubprocess_state(m)->enable); |
1154 | | - Py_CLEAR(get_posixsubprocess_state(m)->isenabled); |
1155 | | - return 0; |
1156 | | -} |
1157 | | - |
1158 | | -static void _posixsubprocess_free(void *m) { |
1159 | | - _posixsubprocess_clear((PyObject *)m); |
1160 | | -} |
1161 | | - |
1162 | 1059 | static struct PyModuleDef _posixsubprocessmodule = { |
1163 | 1060 | PyModuleDef_HEAD_INIT, |
1164 | 1061 | .m_name = "_posixsubprocess", |
1165 | 1062 | .m_doc = module_doc, |
1166 | | - .m_size = sizeof(_posixsubprocessstate), |
| 1063 | + .m_size = 0, |
1167 | 1064 | .m_methods = module_methods, |
1168 | 1065 | .m_slots = _posixsubprocess_slots, |
1169 | | - .m_traverse = _posixsubprocess_traverse, |
1170 | | - .m_clear = _posixsubprocess_clear, |
1171 | | - .m_free = _posixsubprocess_free, |
1172 | 1066 | }; |
1173 | 1067 |
|
1174 | 1068 | PyMODINIT_FUNC |
|
0 commit comments