Add a simple QuicTransport server for testing and demo purposes.

The server currently has two modes, echo and discard.  I've changed the integration test to use the simple server instead of a session with a mock visitor.

This CL also adds some of the missing APIs and fixes some of the bugs I've found while doing this.

gfe-relnote: n/a (code not used)
PiperOrigin-RevId: 278456752
Change-Id: Idf9aa654aa0d66673f300f2f5425f0716d6c3e14
diff --git a/quic/quic_transport/quic_transport_client_session.cc b/quic/quic_transport/quic_transport_client_session.cc
index f738371..72ed9c5 100644
--- a/quic/quic_transport/quic_transport_client_session.cc
+++ b/quic/quic_transport/quic_transport_client_session.cc
@@ -16,9 +16,11 @@
 #include "net/third_party/quiche/src/quic/core/quic_session.h"
 #include "net/third_party/quiche/src/quic/core/quic_types.h"
 #include "net/third_party/quiche/src/quic/core/quic_versions.h"
+#include "net/third_party/quiche/src/quic/platform/api/quic_bug_tracker.h"
 #include "net/third_party/quiche/src/quic/platform/api/quic_logging.h"
 #include "net/third_party/quiche/src/quic/platform/api/quic_string_piece.h"
 #include "net/third_party/quiche/src/quic/platform/api/quic_text_utils.h"
+#include "net/third_party/quiche/src/quic/quic_transport/quic_transport_protocol.h"
 #include "net/third_party/quiche/src/quic/quic_transport/quic_transport_stream.h"
 
 namespace quic {
@@ -65,17 +67,15 @@
 
 QuicStream* QuicTransportClientSession::CreateIncomingStream(QuicStreamId id) {
   QUIC_DVLOG(1) << "Creating incoming QuicTransport stream " << id;
-  auto stream = std::make_unique<QuicTransportStream>(id, this, this);
-  QuicTransportStream* stream_ptr = stream.get();
-  ActivateStream(std::move(stream));
-  if (stream_ptr->type() == BIDIRECTIONAL) {
-    incoming_bidirectional_streams_.push_back(stream_ptr);
+  QuicTransportStream* stream = CreateStream(id);
+  if (stream->type() == BIDIRECTIONAL) {
+    incoming_bidirectional_streams_.push_back(stream);
     visitor_->OnIncomingBidirectionalStreamAvailable();
   } else {
-    incoming_unidirectional_streams_.push_back(stream_ptr);
+    incoming_unidirectional_streams_.push_back(stream);
     visitor_->OnIncomingUnidirectionalStreamAvailable();
   }
-  return stream_ptr;
+  return stream;
 }
 
 void QuicTransportClientSession::OnCryptoHandshakeEvent(
@@ -108,6 +108,31 @@
   return stream;
 }
 
+QuicTransportStream*
+QuicTransportClientSession::OpenOutgoingBidirectionalStream() {
+  if (!CanOpenNextOutgoingBidirectionalStream()) {
+    QUIC_BUG << "Attempted to open a stream in violation of flow control";
+    return nullptr;
+  }
+  return CreateStream(GetNextOutgoingBidirectionalStreamId());
+}
+
+QuicTransportStream*
+QuicTransportClientSession::OpenOutgoingUnidirectionalStream() {
+  if (!CanOpenNextOutgoingUnidirectionalStream()) {
+    QUIC_BUG << "Attempted to open a stream in violation of flow control";
+    return nullptr;
+  }
+  return CreateStream(GetNextOutgoingUnidirectionalStreamId());
+}
+
+QuicTransportStream* QuicTransportClientSession::CreateStream(QuicStreamId id) {
+  auto stream = std::make_unique<QuicTransportStream>(id, this, this);
+  QuicTransportStream* stream_ptr = stream.get();
+  ActivateStream(std::move(stream));
+  return stream_ptr;
+}
+
 std::string QuicTransportClientSession::SerializeClientIndication() {
   std::string serialized_origin = origin_.Serialize();
   if (serialized_origin.size() > std::numeric_limits<uint16_t>::max()) {
@@ -151,8 +176,11 @@
   }
 
   auto client_indication_owned = std::make_unique<ClientIndication>(
-      /*stream_id=*/ClientIndicationStream(), this, /*is_static=*/false,
-      WRITE_UNIDIRECTIONAL);
+      /*stream_id=*/GetNextOutgoingUnidirectionalStreamId(), this,
+      /*is_static=*/false, WRITE_UNIDIRECTIONAL);
+  QUIC_BUG_IF(client_indication_owned->id() != ClientIndicationStream())
+      << "Client indication stream is " << client_indication_owned->id()
+      << " instead of expected " << ClientIndicationStream();
   ClientIndication* client_indication = client_indication_owned.get();
   ActivateStream(std::move(client_indication_owned));