@@ -27,12 +27,17 @@ static int s_stream_write_data(
2727
2828static void s_stream_cross_thread_work_task (struct aws_channel_task * task , void * arg , enum aws_task_status status );
2929static struct aws_h2err s_send_rst_and_close_stream (struct aws_h2_stream * stream , struct aws_h2err stream_error );
30- static int s_stream_reset_stream_internal (struct aws_http_stream * stream_base , struct aws_h2err stream_error );
30+ static int s_stream_reset_stream_internal (
31+ struct aws_http_stream * stream_base ,
32+ struct aws_h2err stream_error ,
33+ bool cancelling );
34+ static void s_stream_cancel (struct aws_http_stream * stream , int error_code );
3135
3236struct aws_http_stream_vtable s_h2_stream_vtable = {
3337 .destroy = s_stream_destroy ,
3438 .update_window = s_stream_update_window ,
3539 .activate = aws_h2_stream_activate ,
40+ .cancel = s_stream_cancel ,
3641 .http1_write_chunk = NULL ,
3742 .http2_reset_stream = s_stream_reset_stream ,
3843 .http2_get_received_error_code = s_stream_get_received_error_code ,
@@ -526,12 +531,16 @@ static void s_stream_update_window(struct aws_http_stream *stream_base, size_t i
526531 .h2_code = AWS_HTTP2_ERR_INTERNAL_ERROR ,
527532 };
528533 /* Only when stream is not initialized reset will fail. So, we can assert it to be succeed. */
529- AWS_FATAL_ASSERT (s_stream_reset_stream_internal (stream_base , stream_error ) == AWS_OP_SUCCESS );
534+ AWS_FATAL_ASSERT (
535+ s_stream_reset_stream_internal (stream_base , stream_error , false /*cancelling*/ ) == AWS_OP_SUCCESS );
530536 }
531537 return ;
532538}
533539
534- static int s_stream_reset_stream_internal (struct aws_http_stream * stream_base , struct aws_h2err stream_error ) {
540+ static int s_stream_reset_stream_internal (
541+ struct aws_http_stream * stream_base ,
542+ struct aws_h2err stream_error ,
543+ bool cancelling ) {
535544
536545 struct aws_h2_stream * stream = AWS_CONTAINER_OF (stream_base , struct aws_h2_stream , base );
537546 struct aws_h2_connection * connection = s_get_h2_connection (stream );
@@ -553,21 +562,25 @@ static int s_stream_reset_stream_internal(struct aws_http_stream *stream_base, s
553562 } /* END CRITICAL SECTION */
554563
555564 if (stream_is_init ) {
565+ if (cancelling ) {
566+ /* Not an error if we are just cancelling. */
567+ AWS_LOGF_DEBUG (AWS_LS_HTTP_STREAM , "id=%p: Stream not in process, nothing to cancel." , (void * )stream );
568+ return AWS_OP_SUCCESS ;
569+ }
556570 AWS_H2_STREAM_LOG (
557571 ERROR , stream , "Reset stream failed. Stream is in initialized state, please activate the stream first." );
558572 return aws_raise_error (AWS_ERROR_INVALID_STATE );
559573 }
574+ if (reset_called ) {
575+ AWS_H2_STREAM_LOG (DEBUG , stream , "Reset stream ignored. Reset stream has been called already." );
576+ }
577+
560578 if (cross_thread_work_should_schedule ) {
561579 AWS_H2_STREAM_LOG (TRACE , stream , "Scheduling stream cross-thread work task" );
562580 /* increment the refcount of stream to keep it alive until the task runs */
563581 aws_atomic_fetch_add (& stream -> base .refcount , 1 );
564582 aws_channel_schedule_task_now (connection -> base .channel_slot -> channel , & stream -> cross_thread_work_task );
565- return AWS_OP_SUCCESS ;
566583 }
567- if (reset_called ) {
568- AWS_H2_STREAM_LOG (DEBUG , stream , "Reset stream ignored. Reset stream has been called already." );
569- }
570-
571584 return AWS_OP_SUCCESS ;
572585}
573586
@@ -583,7 +596,16 @@ static int s_stream_reset_stream(struct aws_http_stream *stream_base, uint32_t h
583596 (void * )stream_base ,
584597 aws_http2_error_code_to_str (http2_error ),
585598 http2_error );
586- return s_stream_reset_stream_internal (stream_base , stream_error );
599+ return s_stream_reset_stream_internal (stream_base , stream_error , false /*cancelling*/ );
600+ }
601+
602+ void s_stream_cancel (struct aws_http_stream * stream_base , int error_code ) {
603+ struct aws_h2err stream_error = {
604+ .aws_code = error_code ,
605+ .h2_code = AWS_HTTP2_ERR_CANCEL ,
606+ };
607+ s_stream_reset_stream_internal (stream_base , stream_error , true /*cancelling*/ );
608+ return ;
587609}
588610
589611static int s_stream_get_received_error_code (struct aws_http_stream * stream_base , uint32_t * out_http2_error ) {
0 commit comments