// Copyright 2019 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_receive_control_stream.h"

#include <utility>

#include "absl/strings/numbers.h"
#include "absl/strings/str_split.h"
#include "absl/strings/string_view.h"
#include "quic/core/http/http_constants.h"
#include "quic/core/http/http_decoder.h"
#include "quic/core/http/quic_spdy_session.h"
#include "quic/core/quic_types.h"
#include "quic/platform/api/quic_flag_utils.h"
#include "quic/platform/api/quic_flags.h"
#include "common/platform/api/quiche_text_utils.h"

namespace quic {

QuicReceiveControlStream::QuicReceiveControlStream(
    PendingStream* pending,
    QuicSpdySession* spdy_session)
    : QuicStream(pending,
                 spdy_session,
                 READ_UNIDIRECTIONAL,
                 /*is_static=*/true),
      settings_frame_received_(false),
      decoder_(this),
      spdy_session_(spdy_session) {
  sequencer()->set_level_triggered(true);
}

QuicReceiveControlStream::~QuicReceiveControlStream() {}

void QuicReceiveControlStream::OnStreamReset(
    const QuicRstStreamFrame& /*frame*/) {
  stream_delegate()->OnStreamError(
      QUIC_HTTP_CLOSED_CRITICAL_STREAM,
      "RESET_STREAM received for receive control stream");
}

void QuicReceiveControlStream::OnDataAvailable() {
  iovec iov;
  while (!reading_stopped() && decoder_.error() == QUIC_NO_ERROR &&
         sequencer()->GetReadableRegion(&iov)) {
    QUICHE_DCHECK(!sequencer()->IsClosed());

    QuicByteCount processed_bytes = decoder_.ProcessInput(
        reinterpret_cast<const char*>(iov.iov_base), iov.iov_len);
    sequencer()->MarkConsumed(processed_bytes);

    if (!session()->connection()->connected()) {
      return;
    }

    // The only reason QuicReceiveControlStream pauses HttpDecoder is an error,
    // in which case the connection would have already been closed.
    QUICHE_DCHECK_EQ(iov.iov_len, processed_bytes);
  }
}

void QuicReceiveControlStream::OnError(HttpDecoder* decoder) {
  stream_delegate()->OnStreamError(decoder->error(), decoder->error_detail());
}

bool QuicReceiveControlStream::OnCancelPushFrame(const CancelPushFrame& frame) {
  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnCancelPushFrameReceived(frame);
  }

  // TODO(b/151841240): Handle CANCEL_PUSH frames instead of ignoring them.
  return ValidateFrameType(HttpFrameType::CANCEL_PUSH);
}

bool QuicReceiveControlStream::OnMaxPushIdFrame(const MaxPushIdFrame& frame) {
  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnMaxPushIdFrameReceived(frame);
  }

  if (!ValidateFrameType(HttpFrameType::MAX_PUSH_ID)) {
    return false;
  }

  return spdy_session()->OnMaxPushIdFrame(frame.push_id);
}

bool QuicReceiveControlStream::OnGoAwayFrame(const GoAwayFrame& frame) {
  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnGoAwayFrameReceived(frame);
  }

  if (!ValidateFrameType(HttpFrameType::GOAWAY)) {
    return false;
  }

  spdy_session()->OnHttp3GoAway(frame.id);
  return true;
}

bool QuicReceiveControlStream::OnSettingsFrameStart(
    QuicByteCount /*header_length*/) {
  return ValidateFrameType(HttpFrameType::SETTINGS);
}

bool QuicReceiveControlStream::OnSettingsFrame(const SettingsFrame& frame) {
  QUIC_DVLOG(1) << "Control Stream " << id()
                << " received settings frame: " << frame;
  return spdy_session_->OnSettingsFrame(frame);
}

bool QuicReceiveControlStream::OnDataFrameStart(QuicByteCount /*header_length*/,
                                                QuicByteCount
                                                /*payload_length*/) {
  return ValidateFrameType(HttpFrameType::DATA);
}

bool QuicReceiveControlStream::OnDataFramePayload(
    absl::string_view /*payload*/) {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnDataFrameEnd() {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnHeadersFrameStart(
    QuicByteCount /*header_length*/,
    QuicByteCount
    /*payload_length*/) {
  return ValidateFrameType(HttpFrameType::HEADERS);
}

bool QuicReceiveControlStream::OnHeadersFramePayload(
    absl::string_view /*payload*/) {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnHeadersFrameEnd() {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnPushPromiseFrameStart(
    QuicByteCount /*header_length*/) {
  return ValidateFrameType(HttpFrameType::PUSH_PROMISE);
}

bool QuicReceiveControlStream::OnPushPromiseFramePushId(
    PushId /*push_id*/,
    QuicByteCount /*push_id_length*/,
    QuicByteCount /*header_block_length*/) {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnPushPromiseFramePayload(
    absl::string_view /*payload*/) {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnPushPromiseFrameEnd() {
  QUICHE_NOTREACHED();
  return false;
}

bool QuicReceiveControlStream::OnPriorityUpdateFrameStart(
    QuicByteCount /*header_length*/) {
  return ValidateFrameType(HttpFrameType::PRIORITY_UPDATE);
}

bool QuicReceiveControlStream::OnPriorityUpdateFrame(
    const PriorityUpdateFrame& frame) {
  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnPriorityUpdateFrameReceived(frame);
  }

  // TODO(b/147306124): Use a proper structured headers parser instead.
  for (absl::string_view key_value :
       absl::StrSplit(frame.priority_field_value, ',')) {
    std::vector<absl::string_view> key_and_value =
        absl::StrSplit(key_value, '=');
    if (key_and_value.size() != 2) {
      continue;
    }

    absl::string_view key = key_and_value[0];
    quiche::QuicheTextUtils::RemoveLeadingAndTrailingWhitespace(&key);
    if (key != "u") {
      continue;
    }

    absl::string_view value = key_and_value[1];
    int urgency;
    if (!absl::SimpleAtoi(value, &urgency) || urgency < 0 || urgency > 7) {
      stream_delegate()->OnStreamError(
          QUIC_INVALID_PRIORITY_UPDATE,
          "Invalid value for PRIORITY_UPDATE urgency parameter.");
      return false;
    }

    if (frame.prioritized_element_type == REQUEST_STREAM) {
      return spdy_session_->OnPriorityUpdateForRequestStream(
          frame.prioritized_element_id, urgency);
    } else {
      return spdy_session_->OnPriorityUpdateForPushStream(
          frame.prioritized_element_id, urgency);
    }
  }

  // Ignore frame if no urgency parameter can be parsed.
  return true;
}

bool QuicReceiveControlStream::OnAcceptChFrameStart(
    QuicByteCount /* header_length */) {
  return ValidateFrameType(HttpFrameType::ACCEPT_CH);
}

bool QuicReceiveControlStream::OnAcceptChFrame(const AcceptChFrame& frame) {
  QUICHE_DCHECK_EQ(Perspective::IS_CLIENT, spdy_session()->perspective());

  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnAcceptChFrameReceived(frame);
  }

  spdy_session()->OnAcceptChFrame(frame);
  return true;
}

void QuicReceiveControlStream::OnWebTransportStreamFrameType(
    QuicByteCount /*header_length*/,
    WebTransportSessionId /*session_id*/) {
  QUIC_BUG(WEBTRANSPORT_STREAM on Control Stream)
      << "Parsed WEBTRANSPORT_STREAM on a control stream.";
}

bool QuicReceiveControlStream::OnUnknownFrameStart(
    uint64_t frame_type,
    QuicByteCount /*header_length*/,
    QuicByteCount payload_length) {
  if (spdy_session()->debug_visitor()) {
    spdy_session()->debug_visitor()->OnUnknownFrameReceived(id(), frame_type,
                                                            payload_length);
  }

  return ValidateFrameType(static_cast<HttpFrameType>(frame_type));
}

bool QuicReceiveControlStream::OnUnknownFramePayload(
    absl::string_view /*payload*/) {
  // Ignore unknown frame types.
  return true;
}

bool QuicReceiveControlStream::OnUnknownFrameEnd() {
  // Ignore unknown frame types.
  return true;
}

bool QuicReceiveControlStream::ValidateFrameType(HttpFrameType frame_type) {
  // Certain frame types are forbidden.
  if ((frame_type == HttpFrameType::DATA ||
       frame_type == HttpFrameType::HEADERS ||
       frame_type == HttpFrameType::PUSH_PROMISE) ||
      (spdy_session()->perspective() == Perspective::IS_CLIENT &&
       frame_type == HttpFrameType::MAX_PUSH_ID) ||
      (spdy_session()->perspective() == Perspective::IS_SERVER &&
       frame_type == HttpFrameType::ACCEPT_CH)) {
    stream_delegate()->OnStreamError(
        QUIC_HTTP_FRAME_UNEXPECTED_ON_CONTROL_STREAM,
        absl::StrCat("Invalid frame type ", static_cast<int>(frame_type),
                     " received on control stream."));
    return false;
  }

  if (settings_frame_received_) {
    if (frame_type == HttpFrameType::SETTINGS) {
      // SETTINGS frame may only be the first frame on the control stream.
      stream_delegate()->OnStreamError(
          QUIC_HTTP_INVALID_FRAME_SEQUENCE_ON_CONTROL_STREAM,
          "SETTINGS frame can only be received once.");
      return false;
    }
    return true;
  }

  if (frame_type == HttpFrameType::SETTINGS) {
    settings_frame_received_ = true;
    return true;
  }
  stream_delegate()->OnStreamError(
      QUIC_HTTP_MISSING_SETTINGS_FRAME,
      absl::StrCat("First frame received on control stream is type ",
                   static_cast<int>(frame_type), ", but it must be SETTINGS."));
  return false;
}

}  // namespace quic
