// Copyright (c) 2016 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "quic/core/http/quic_spdy_server_stream_base.h"

#include "absl/strings/string_view.h"
#include "quic/core/http/quic_spdy_session.h"
#include "quic/core/quic_error_codes.h"
#include "quic/platform/api/quic_flag_utils.h"
#include "quic/platform/api/quic_flags.h"
#include "quic/platform/api/quic_logging.h"
#include "common/quiche_text_utils.h"

namespace quic {

QuicSpdyServerStreamBase::QuicSpdyServerStreamBase(QuicStreamId id,
                                                   QuicSpdySession* session,
                                                   StreamType type)
    : QuicSpdyStream(id, session, type) {}

QuicSpdyServerStreamBase::QuicSpdyServerStreamBase(PendingStream* pending,
                                                   QuicSpdySession* session)
    : QuicSpdyStream(pending, session) {}

void QuicSpdyServerStreamBase::CloseWriteSide() {
  if (!fin_received() && !rst_received() && sequencer()->ignore_read_data() &&
      !rst_sent()) {
    // Early cancel the stream if it has stopped reading before receiving FIN
    // or RST.
    QUICHE_DCHECK(fin_sent() || !session()->connection()->connected());
    // Tell the peer to stop sending further data.
    QUIC_DVLOG(1) << " Server: Send QUIC_STREAM_NO_ERROR on stream " << id();
    MaybeSendStopSending(QUIC_STREAM_NO_ERROR);
  }

  QuicSpdyStream::CloseWriteSide();
}

void QuicSpdyServerStreamBase::StopReading() {
  if (!fin_received() && !rst_received() && write_side_closed() &&
      !rst_sent()) {
    QUICHE_DCHECK(fin_sent());
    // Tell the peer to stop sending further data.
    QUIC_DVLOG(1) << " Server: Send QUIC_STREAM_NO_ERROR on stream " << id();
    MaybeSendStopSending(QUIC_STREAM_NO_ERROR);
  }
  QuicSpdyStream::StopReading();
}

bool QuicSpdyServerStreamBase::AreHeadersValid(
    const QuicHeaderList& header_list) const {
  if (!GetQuicReloadableFlag(quic_verify_request_headers_2)) {
    return true;
  }
  QUIC_RELOADABLE_FLAG_COUNT_N(quic_verify_request_headers_2, 2, 3);
  if (!QuicSpdyStream::AreHeadersValid(header_list)) {
    return false;
  }

  bool saw_connect = false;
  bool saw_protocol = false;
  bool saw_path = false;
  bool saw_scheme = false;
  bool saw_method = false;
  bool saw_authority = false;
  bool is_extended_connect = false;
  // Check if it is missing any required headers and if there is any disallowed
  // ones.
  for (const std::pair<std::string, std::string>& pair : header_list) {
    if (pair.first == ":method") {
      saw_method = true;
      if (pair.second == "CONNECT") {
        saw_connect = true;
        if (saw_protocol) {
          is_extended_connect = true;
        }
      }
    } else if (pair.first == ":protocol") {
      saw_protocol = true;
      if (saw_connect) {
        is_extended_connect = true;
      }
    } else if (pair.first == ":scheme") {
      saw_scheme = true;
    } else if (pair.first == ":path") {
      saw_path = true;
    } else if (pair.first == ":authority") {
      saw_authority = true;
    } else if (absl::StrContains(pair.first, ":")) {
      QUIC_DLOG(ERROR) << "Unexpected ':' in header " << pair.first << ".";
      return false;
    }
    if (is_extended_connect) {
      if (!spdy_session()->allow_extended_connect()) {
        QUIC_DLOG(ERROR)
            << "Received extended-CONNECT request while it is disabled.";
        return false;
      }
    } else if (saw_method && !saw_connect) {
      if (saw_protocol) {
        QUIC_DLOG(ERROR) << "Receive non-CONNECT request with :protocol.";
        return false;
      }
    }
  }

  if (is_extended_connect) {
    if (saw_scheme && saw_path && saw_authority) {
      // Saw all the required pseudo headers.
      return true;
    }
    QUIC_DLOG(ERROR) << "Missing required pseudo headers for extended-CONNECT.";
    return false;
  }
  // This is a vanilla CONNECT or non-CONNECT request.
  if (saw_connect) {
    // Check vanilla CONNECT.
    if (saw_path || saw_scheme) {
      QUIC_DLOG(ERROR)
          << "Received invalid CONNECT request with disallowed pseudo header.";
      return false;
    }
    return true;
  }
  // Check non-CONNECT request.
  if (saw_method && saw_authority && saw_path && saw_scheme) {
    return true;
  }
  QUIC_LOG(ERROR) << "Missing required pseudo headers.";
  return false;
}

}  // namespace quic
