Add minimal spdy priority set by gws response header for initial cwnd bootstrapping for http2. also store spdy priority within spdydispatcher::sessiondata. no production behavior change unless we start an additional gws experiment. protected by gfe2_restart_flag_h2_adjust_initial_cwnd_by_gws.

While QUIC stores SPDY within spdy::PriorityWriteScheduler<...>, SPDY priority is stored in a map from stream_id to SessionData owned by SpdyClientDispatcher in this change because
(1) H2 uses LIFOWriteScheduler<...> by default, which ignores precedence (http://shortn/_2Ny3X9xBh6).
(2) We only need CWND bootstrapping for traffic from client, and hence only SpdyClientDispatcher populates the SPDY priority.

PiperOrigin-RevId: 316117083
Change-Id: I232e421b16edecc5f7146ce4fb36592a71a7e86f
diff --git a/spdy/core/fifo_write_scheduler.h b/spdy/core/fifo_write_scheduler.h
index a2c6989..7b31891 100644
--- a/spdy/core/fifo_write_scheduler.h
+++ b/spdy/core/fifo_write_scheduler.h
@@ -29,6 +29,8 @@
                       const StreamPrecedenceType& precedence) override;
   void UnregisterStream(StreamIdType stream_id) override;
   bool StreamRegistered(StreamIdType stream_id) const override;
+  // Stream precedence is available but note that it is not used for scheduling
+  // in this scheduler.
   StreamPrecedenceType GetStreamPrecedence(
       StreamIdType stream_id) const override;
   void UpdateStreamPrecedence(StreamIdType stream_id,
@@ -51,20 +53,26 @@
   std::string DebugString() const override;
 
  private:
+  struct StreamInfo {
+    SpdyPriority priority;
+    int64_t event_time;  // read/write event time (us since Unix epoch).
+  };
+
   std::set<StreamIdType> ready_streams_;
-  // This map maps stream ID to read/write event time (us since Unix epoch).
-  std::map<StreamIdType, int64_t> registered_streams_;
+  std::map<StreamIdType, StreamInfo> registered_streams_;
 };
 
 template <typename StreamIdType>
 void FifoWriteScheduler<StreamIdType>::RegisterStream(
     StreamIdType stream_id,
-    const StreamPrecedenceType& /*precedence*/) {
+    const StreamPrecedenceType& precedence) {
   if (StreamRegistered(stream_id)) {
     SPDY_BUG << "Stream " << stream_id << " already registered";
     return;
   }
-  registered_streams_.emplace_hint(registered_streams_.end(), stream_id, 0);
+  registered_streams_.emplace_hint(
+      registered_streams_.end(), stream_id,
+      StreamInfo{/*priority=*/precedence.spdy3_priority(), /*event_time=*/0});
 }
 
 template <typename StreamIdType>
@@ -88,14 +96,26 @@
 template <typename StreamIdType>
 typename FifoWriteScheduler<StreamIdType>::StreamPrecedenceType
 FifoWriteScheduler<StreamIdType>::GetStreamPrecedence(
-    StreamIdType /*stream_id*/) const {
-  return StreamPrecedenceType(kV3LowestPriority);
+    StreamIdType stream_id) const {
+  auto it = registered_streams_.find(stream_id);
+  if (it == registered_streams_.end()) {
+    SPDY_DVLOG(1) << "Stream " << stream_id << " not registered";
+    return StreamPrecedenceType(kV3LowestPriority);
+  }
+  return StreamPrecedenceType(it->second.priority);
 }
 
 template <typename StreamIdType>
 void FifoWriteScheduler<StreamIdType>::UpdateStreamPrecedence(
-    StreamIdType /*stream_id*/,
-    const StreamPrecedenceType& /*precedence*/) {}
+    StreamIdType stream_id,
+    const StreamPrecedenceType& precedence) {
+  auto it = registered_streams_.find(stream_id);
+  if (it == registered_streams_.end()) {
+    SPDY_DVLOG(1) << "Stream " << stream_id << " not registered";
+    return;
+  }
+  it->second.priority = precedence.spdy3_priority();
+}
 
 template <typename StreamIdType>
 std::vector<StreamIdType> FifoWriteScheduler<StreamIdType>::GetStreamChildren(
@@ -109,7 +129,7 @@
     int64_t now_in_usec) {
   auto it = registered_streams_.find(stream_id);
   if (it != registered_streams_.end()) {
-    it->second = now_in_usec;
+    it->second.event_time = now_in_usec;
   } else {
     SPDY_BUG << "Stream " << stream_id << " is not registered";
   }
@@ -128,7 +148,8 @@
     if (stream_id <= it->first) {
       break;
     }
-    latest_event_time_us = std::max(latest_event_time_us, it->second);
+    latest_event_time_us =
+        std::max(latest_event_time_us, it->second.event_time);
   }
   return latest_event_time_us;
 }