This is an automated email from the ASF dual-hosted git repository.

masaori pushed a commit to branch quic-latest
in repository https://gitbox.apache.org/repos/asf/trafficserver.git


The following commit(s) were added to refs/heads/quic-latest by this push:
     new 71a6931  Send CONNECTION/APPLICATION_CLOSE frame
71a6931 is described below

commit 71a69310413b5137f4d54d97cb0f5061447ba056
Author: Masaori Koshiba <masa...@apache.org>
AuthorDate: Tue Apr 10 12:09:24 2018 +0900

    Send CONNECTION/APPLICATION_CLOSE frame
---
 iocore/net/P_QUICNetVConnection.h |  1 +
 iocore/net/QUICNetVConnection.cc  | 72 +++++++++++++++++----------------------
 2 files changed, 33 insertions(+), 40 deletions(-)

diff --git a/iocore/net/P_QUICNetVConnection.h 
b/iocore/net/P_QUICNetVConnection.h
index 9d8523a..05f49d1 100644
--- a/iocore/net/P_QUICNetVConnection.h
+++ b/iocore/net/P_QUICNetVConnection.h
@@ -286,6 +286,7 @@ private:
   void _store_frame(ats_unique_buf &buf, size_t &len, bool &retransmittable, 
QUICPacketType &current_packet_type,
                     QUICFrameUPtr frame);
   void _packetize_frames();
+  void _packetize_closing_frame();
   QUICPacketUPtr _build_packet(ats_unique_buf buf, size_t len, bool 
retransmittable,
                                QUICPacketType type = 
QUICPacketType::UNINITIALIZED);
 
diff --git a/iocore/net/QUICNetVConnection.cc b/iocore/net/QUICNetVConnection.cc
index 8c19e6c..86e1a30 100644
--- a/iocore/net/QUICNetVConnection.cc
+++ b/iocore/net/QUICNetVConnection.cc
@@ -624,8 +624,6 @@ QUICNetVConnection::state_connection_closing(int event, 
Event *data)
   case QUIC_EVENT_PACKET_WRITE_READY:
     this->_close_packet_write_ready(data);
     this->_state_closing_send_packet();
-    // Reschedule WRITE_READY
-    this->_schedule_packet_write_ready(true);
     break;
   case QUIC_EVENT_PATH_VALIDATION_TIMEOUT:
     this->_close_path_validation_timeout(data);
@@ -1045,6 +1043,10 @@ QUICNetVConnection::_state_handshake_send_retry_packet()
 QUICErrorUPtr
 QUICNetVConnection::_state_closing_send_packet()
 {
+  this->_packetize_closing_frame();
+
+  // TODO: should credit of congestion controller be checked?
+
   // During the closing period, an endpoint that sends a
   // closing frame SHOULD respond to any packet that it receives with
   // another packet containing a closing frame.  To minimize the state
@@ -1094,22 +1096,9 @@ QUICNetVConnection::_store_frame(ats_unique_buf &buf, 
size_t &len, bool &retrans
   frame->store(buf.get() + len, &l);
   len += l;
 
-  if (frame->type() == QUICFrameType::CONNECTION_CLOSE || frame->type() == 
QUICFrameType::APPLICATION_CLOSE) {
-    this->_transmit_packet(this->_build_packet(std::move(buf), len, 
retransmittable, previous_packet_type));
-    retransmittable = false;
-    len             = 0;
-    buf             = ats_unique_malloc(max_size);
-    frame->store(buf.get(), &l);
-    this->_the_final_packet = this->_build_packet(std::move(buf), l, false);
-  }
-
   return;
 }
 
-// 1. Dequeue frame from _stream_frame_send_queue and _frame_send_queue
-// 2. Put frames into buffer as many as possible
-// 3. Build packet with the buffer
-// 4. Enqueue the packet via transmit_packet
 void
 QUICNetVConnection::_packetize_frames()
 {
@@ -1146,27 +1135,12 @@ QUICNetVConnection::_packetize_frames()
   while (frame) {
     ++frame_count;
     this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
-    if (this->_the_final_packet) {
-      return;
-    }
     if (frame_count >= FRAME_PER_EVENT) {
       break;
     }
     frame = 
this->_path_validator->generate_frame(this->_remote_flow_controller->credit(), 
this->_maximum_stream_frame_data_size());
   }
 
-  // CONNECTION_CLOSE, APPLICATION_CLOSE
-  if (this->_connection_error) {
-    QUICFrameUPtr frame = QUICFrameFactory::create_null_ack_frame();
-    if (this->_connection_error->cls == QUICErrorClass::APPLICATION) {
-      frame = 
QUICFrameFactory::create_application_close_frame(std::move(this->_connection_error));
-    } else {
-      frame = 
QUICFrameFactory::create_connection_close_frame(std::move(this->_connection_error));
-    }
-    ++frame_count;
-    this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
-  }
-
   // NEW_CONNECTION_ID
   if (this->_alt_con_manager) {
     frame =
@@ -1174,9 +1148,6 @@ QUICNetVConnection::_packetize_frames()
     while (frame) {
       ++frame_count;
       this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
-      if (this->_the_final_packet) {
-        return;
-      }
       if (frame_count >= FRAME_PER_EVENT) {
         break;
       }
@@ -1191,9 +1162,6 @@ QUICNetVConnection::_packetize_frames()
   while (frame) {
     ++frame_count;
     this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
-    if (this->_the_final_packet) {
-      return;
-    }
     if (frame_count >= FRAME_PER_EVENT) {
       break;
     }
@@ -1215,9 +1183,7 @@ QUICNetVConnection::_packetize_frames()
       this->_stream_manager->add_total_offset_sent(frame_size);
     }
     this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
-    if (this->_the_final_packet) {
-      return;
-    }
+
     if (frame_count >= FRAME_PER_EVENT) {
       break;
     }
@@ -1237,6 +1203,32 @@ QUICNetVConnection::_packetize_frames()
   }
 }
 
+void
+QUICNetVConnection::_packetize_closing_frame()
+{
+  SCOPED_MUTEX_LOCK(packet_transmitter_lock, this->_packet_transmitter_mutex, 
this_ethread());
+  SCOPED_MUTEX_LOCK(frame_transmitter_lock, this->_frame_transmitter_mutex, 
this_ethread());
+
+  if (this->_connection_error == nullptr) {
+    return;
+  }
+
+  QUICFrameUPtr frame = QUICFrameFactory::create_null_ack_frame();
+  if (this->_connection_error->cls == QUICErrorClass::APPLICATION) {
+    frame = 
QUICFrameFactory::create_application_close_frame(std::move(this->_connection_error));
+  } else {
+    frame = 
QUICFrameFactory::create_connection_close_frame(std::move(this->_connection_error));
+  }
+
+  ats_unique_buf buf(nullptr, [](void *p) { ats_free(p); });
+  size_t len                         = 0;
+  bool retransmittable               = false;
+  QUICPacketType current_packet_type = QUICPacketType::UNINITIALIZED;
+  this->_store_frame(buf, len, retransmittable, current_packet_type, 
std::move(frame));
+
+  this->_the_final_packet = this->_build_packet(std::move(buf), len, false);
+}
+
 QUICErrorUPtr
 QUICNetVConnection::_recv_and_ack(QUICPacketUPtr packet)
 {
@@ -1635,6 +1627,7 @@ 
QUICNetVConnection::_switch_to_closing_state(QUICConnectionErrorUPtr error)
     QUICConDebug("Reason was not provided");
   }
   this->_connection_error = std::move(error);
+  this->_schedule_packet_write_ready();
 
   this->remove_from_active_queue();
   this->set_inactivity_timeout(0);
@@ -1647,7 +1640,6 @@ 
QUICNetVConnection::_switch_to_closing_state(QUICConnectionErrorUPtr error)
   // This states SHOULD persist for three times the
   // current Retransmission Timeout (RTO) interval as defined in
   // [QUIC-RECOVERY].
-
   this->_schedule_closing_timeout(3 * rto);
 }
 

-- 
To stop receiving notification emails like this one, please contact
masa...@apache.org.

Reply via email to