|  | // Copyright (c) 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/qbone/qbone_packet_exchanger.h" | 
|  |  | 
|  | #include <utility> | 
|  |  | 
|  | namespace quic { | 
|  |  | 
|  | bool QbonePacketExchanger::ReadAndDeliverPacket( | 
|  | QboneClientInterface* qbone_client) { | 
|  | bool blocked = false; | 
|  | std::string error; | 
|  | std::unique_ptr<QuicData> packet = ReadPacket(&blocked, &error); | 
|  | if (packet == nullptr) { | 
|  | if (!blocked) { | 
|  | visitor_->OnReadError(error); | 
|  | } | 
|  | return false; | 
|  | } | 
|  | qbone_client->ProcessPacketFromNetwork(packet->AsStringPiece()); | 
|  | return true; | 
|  | } | 
|  |  | 
|  | void QbonePacketExchanger::WritePacketToNetwork(const char* packet, | 
|  | size_t size) { | 
|  | bool blocked = false; | 
|  | std::string error; | 
|  | if (packet_queue_.empty() && !write_blocked_) { | 
|  | if (WritePacket(packet, size, &blocked, &error)) { | 
|  | return; | 
|  | } | 
|  | if (!blocked) { | 
|  | visitor_->OnWriteError(error); | 
|  | return; | 
|  | } | 
|  | write_blocked_ = true; | 
|  | } | 
|  |  | 
|  | // Drop the packet on the floor if the queue if full. | 
|  | if (packet_queue_.size() >= max_pending_packets_) { | 
|  | return; | 
|  | } | 
|  |  | 
|  | auto data_copy = new char[size]; | 
|  | memcpy(data_copy, packet, size); | 
|  | packet_queue_.push_back( | 
|  | std::make_unique<QuicData>(data_copy, size, /* owns_buffer = */ true)); | 
|  | } | 
|  |  | 
|  | void QbonePacketExchanger::SetWritable() { | 
|  | write_blocked_ = false; | 
|  | while (!packet_queue_.empty()) { | 
|  | bool blocked = false; | 
|  | std::string error; | 
|  | if (WritePacket(packet_queue_.front()->data(), | 
|  | packet_queue_.front()->length(), &blocked, &error)) { | 
|  | packet_queue_.pop_front(); | 
|  | } else { | 
|  | if (!blocked) { | 
|  | visitor_->OnWriteError(error); | 
|  | } | 
|  | write_blocked_ = blocked; | 
|  | return; | 
|  | } | 
|  | } | 
|  | } | 
|  |  | 
|  | }  // namespace quic |