@@ -68,8 +68,9 @@ COMPUTE_EVAL_BREAKER(PyInterpreterState *interp,
68
68
_Py_atomic_load_relaxed_int32 (& ceval2 -> gil_drop_request )
69
69
| (_Py_atomic_load_relaxed_int32 (& ceval -> signals_pending )
70
70
&& _Py_ThreadCanHandleSignals (interp ))
71
- | (_Py_atomic_load_relaxed_int32 (& ceval2 -> pending .calls_to_do )
72
- && _Py_ThreadCanHandlePendingCalls ())
71
+ | (_Py_atomic_load_relaxed_int32 (& ceval2 -> pending .calls_to_do ))
72
+ | (_Py_IsMainThread ()
73
+ && _Py_atomic_load_relaxed_int32 (& ceval -> pending_mainthread .calls_to_do ))
73
74
| ceval2 -> pending .async_exc
74
75
| _Py_atomic_load_relaxed_int32 (& ceval2 -> gc_scheduled ));
75
76
}
@@ -95,11 +96,11 @@ RESET_GIL_DROP_REQUEST(PyInterpreterState *interp)
95
96
96
97
97
98
static inline void
98
- SIGNAL_PENDING_CALLS (PyInterpreterState * interp )
99
+ SIGNAL_PENDING_CALLS (struct _pending_calls * pending , PyInterpreterState * interp )
99
100
{
100
101
struct _ceval_runtime_state * ceval = & interp -> runtime -> ceval ;
101
102
struct _ceval_state * ceval2 = & interp -> ceval ;
102
- _Py_atomic_store_relaxed (& ceval2 -> pending . calls_to_do , 1 );
103
+ _Py_atomic_store_relaxed (& pending -> calls_to_do , 1 );
103
104
COMPUTE_EVAL_BREAKER (interp , ceval , ceval2 );
104
105
}
105
106
@@ -109,6 +110,9 @@ UNSIGNAL_PENDING_CALLS(PyInterpreterState *interp)
109
110
{
110
111
struct _ceval_runtime_state * ceval = & interp -> runtime -> ceval ;
111
112
struct _ceval_state * ceval2 = & interp -> ceval ;
113
+ if (_Py_IsMainInterpreter (interp )) {
114
+ _Py_atomic_store_relaxed (& ceval -> pending_mainthread .calls_to_do , 0 );
115
+ }
112
116
_Py_atomic_store_relaxed (& ceval2 -> pending .calls_to_do , 0 );
113
117
COMPUTE_EVAL_BREAKER (interp , ceval , ceval2 );
114
118
}
@@ -804,6 +808,11 @@ _PyEval_AddPendingCall(PyInterpreterState *interp,
804
808
{
805
809
assert (!mainthreadonly || _Py_IsMainInterpreter (interp ));
806
810
struct _pending_calls * pending = & interp -> ceval .pending ;
811
+ if (mainthreadonly ) {
812
+ /* The main thread only exists in the main interpreter. */
813
+ assert (_Py_IsMainInterpreter (interp ));
814
+ pending = & _PyRuntime .ceval .pending_mainthread ;
815
+ }
807
816
/* Ensure that _PyEval_InitState() was called
808
817
and that _PyEval_FiniState() is not called yet. */
809
818
assert (pending -> lock != NULL );
@@ -813,7 +822,7 @@ _PyEval_AddPendingCall(PyInterpreterState *interp,
813
822
PyThread_release_lock (pending -> lock );
814
823
815
824
/* signal main loop */
816
- SIGNAL_PENDING_CALLS (interp );
825
+ SIGNAL_PENDING_CALLS (pending , interp );
817
826
return result ;
818
827
}
819
828
@@ -845,10 +854,15 @@ handle_signals(PyThreadState *tstate)
845
854
static inline int
846
855
has_pending_calls (PyInterpreterState * interp )
847
856
{
848
- if (_Py_atomic_load_relaxed_int32 (& interp -> ceval .pending .calls_to_do )) {
857
+ struct _pending_calls * pending = & interp -> ceval .pending ;
858
+ if (_Py_atomic_load_relaxed_int32 (& pending -> calls_to_do )) {
849
859
return 1 ;
850
860
}
851
- return 0 ;
861
+ if (!_Py_IsMainThread ()) {
862
+ return 0 ;
863
+ }
864
+ pending = & _PyRuntime .ceval .pending_mainthread ;
865
+ return _Py_atomic_load_relaxed_int32 (& pending -> calls_to_do );
852
866
}
853
867
854
868
static int
@@ -879,11 +893,7 @@ static int
879
893
make_pending_calls (PyInterpreterState * interp )
880
894
{
881
895
struct _pending_calls * pending = & interp -> ceval .pending ;
882
-
883
- /* only execute pending calls on main thread */
884
- if (!_Py_ThreadCanHandlePendingCalls ()) {
885
- return 0 ;
886
- }
896
+ struct _pending_calls * pending_main = & _PyRuntime .ceval .pending_mainthread ;
887
897
888
898
/* don't perform recursive pending calls */
889
899
if (pending -> busy ) {
@@ -895,13 +905,20 @@ make_pending_calls(PyInterpreterState *interp)
895
905
added in-between re-signals */
896
906
UNSIGNAL_PENDING_CALLS (interp );
897
907
898
- int res = _make_pending_calls (pending );
899
- if (res < 0 ) {
908
+ if (_make_pending_calls (pending ) != 0 ) {
900
909
pending -> busy = 0 ;
901
- SIGNAL_PENDING_CALLS (interp );
910
+ SIGNAL_PENDING_CALLS (pending , interp );
902
911
return -1 ;
903
912
}
904
913
914
+ if (_Py_IsMainThread ()) {
915
+ if (_make_pending_calls (pending_main ) != 0 ) {
916
+ pending -> busy = 0 ;
917
+ SIGNAL_PENDING_CALLS (pending_main , interp );
918
+ return -1 ;
919
+ }
920
+ }
921
+
905
922
pending -> busy = 0 ;
906
923
return 0 ;
907
924
}
0 commit comments