@@ -680,51 +680,66 @@ dummy_func(
680680 PREDICT (LOAD_CONST );
681681 }
682682
683- inst (SEND , (receiver , v -- receiver if (!jump ), retval )) {
683+ family (for_iter , INLINE_CACHE_ENTRIES_FOR_ITER ) = {
684+ SEND ,
685+ SEND_GEN ,
686+ };
687+
688+ inst (SEND , (unused /1 , receiver , v -- receiver , retval )) {
689+ #if ENABLE_SPECIALIZATION
690+ _PySendCache * cache = (_PySendCache * )next_instr ;
691+ if (ADAPTIVE_COUNTER_IS_ZERO (cache -> counter )) {
692+ assert (cframe .use_tracing == 0 );
693+ next_instr -- ;
694+ _Py_Specialize_Send (receiver , next_instr );
695+ DISPATCH_SAME_OPARG ();
696+ }
697+ STAT_INC (SEND , deferred );
698+ DECREMENT_ADAPTIVE_COUNTER (cache -> counter );
699+ #endif /* ENABLE_SPECIALIZATION */
684700 assert (frame != & entry_frame );
685- bool jump = false;
686- PySendResult gen_status ;
687- if (tstate -> c_tracefunc == NULL ) {
688- gen_status = PyIter_Send (receiver , v , & retval );
689- } else {
690- if (Py_IsNone (v ) && PyIter_Check (receiver )) {
691- retval = Py_TYPE (receiver )-> tp_iternext (receiver );
692- }
693- else {
694- retval = PyObject_CallMethodOneArg (receiver , & _Py_ID (send ), v );
695- }
696- if (retval == NULL ) {
697- if (tstate -> c_tracefunc != NULL
698- && _PyErr_ExceptionMatches (tstate , PyExc_StopIteration ))
699- call_exc_trace (tstate -> c_tracefunc , tstate -> c_traceobj , tstate , frame );
700- if (_PyGen_FetchStopIterationValue (& retval ) == 0 ) {
701- gen_status = PYGEN_RETURN ;
702- }
703- else {
704- gen_status = PYGEN_ERROR ;
705- }
701+ if (Py_IsNone (v ) && PyIter_Check (receiver )) {
702+ retval = Py_TYPE (receiver )-> tp_iternext (receiver );
703+ }
704+ else {
705+ retval = PyObject_CallMethodOneArg (receiver , & _Py_ID (send ), v );
706+ }
707+ if (retval == NULL ) {
708+ if (tstate -> c_tracefunc != NULL
709+ && _PyErr_ExceptionMatches (tstate , PyExc_StopIteration ))
710+ call_exc_trace (tstate -> c_tracefunc , tstate -> c_traceobj , tstate , frame );
711+ if (_PyGen_FetchStopIterationValue (& retval ) == 0 ) {
712+ assert (retval != NULL );
713+ JUMPBY (oparg );
706714 }
707715 else {
708- gen_status = PYGEN_NEXT ;
716+ assert (retval == NULL );
717+ goto error ;
709718 }
710719 }
711- if (gen_status == PYGEN_ERROR ) {
712- assert (retval == NULL );
713- goto error ;
714- }
715- Py_DECREF (v );
716- if (gen_status == PYGEN_RETURN ) {
717- assert (retval != NULL );
718- Py_DECREF (receiver );
719- JUMPBY (oparg );
720- jump = true;
721- }
722720 else {
723- assert (gen_status == PYGEN_NEXT );
724721 assert (retval != NULL );
725722 }
726723 }
727724
725+ inst (SEND_GEN , (unused /1 , receiver , v -- receiver )) {
726+ assert (cframe .use_tracing == 0 );
727+ PyGenObject * gen = (PyGenObject * )receiver ;
728+ DEOPT_IF (Py_TYPE (gen ) != & PyGen_Type &&
729+ Py_TYPE (gen ) != & PyCoro_Type , SEND );
730+ DEOPT_IF (gen -> gi_frame_state >= FRAME_EXECUTING , SEND );
731+ STAT_INC (SEND , hit );
732+ _PyInterpreterFrame * gen_frame = (_PyInterpreterFrame * )gen -> gi_iframe ;
733+ frame -> yield_offset = oparg ;
734+ STACK_SHRINK (1 );
735+ _PyFrame_StackPush (gen_frame , v );
736+ gen -> gi_frame_state = FRAME_EXECUTING ;
737+ gen -> gi_exc_state .previous_item = tstate -> exc_info ;
738+ tstate -> exc_info = & gen -> gi_exc_state ;
739+ JUMPBY (INLINE_CACHE_ENTRIES_SEND + oparg );
740+ DISPATCH_INLINED (gen_frame );
741+ }
742+
728743 inst (YIELD_VALUE , (retval -- unused )) {
729744 // NOTE: It's important that YIELD_VALUE never raises an exception!
730745 // The compiler treats any exception raised here as a failed close()
@@ -796,12 +811,13 @@ dummy_func(
796811 }
797812 }
798813
799- inst (CLEANUP_THROW , (sub_iter , last_sent_val , exc_value -- value )) {
814+ inst (CLEANUP_THROW , (sub_iter , last_sent_val , exc_value -- none , value )) {
800815 assert (throwflag );
801816 assert (exc_value && PyExceptionInstance_Check (exc_value ));
802817 if (PyErr_GivenExceptionMatches (exc_value , PyExc_StopIteration )) {
803818 value = Py_NewRef (((PyStopIterationObject * )exc_value )-> value );
804819 DECREF_INPUTS ();
820+ none = Py_NewRef (Py_None );
805821 }
806822 else {
807823 _PyErr_SetRaisedException (tstate , Py_NewRef (exc_value ));
0 commit comments