1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "remoting/base/socket_reader.h" 6 7 #include "base/compiler_specific.h" 8 #include "base/location.h" 9 #include "base/single_thread_task_runner.h" 10 #include "base/thread_task_runner_handle.h" 11 #include "net/base/io_buffer.h" 12 #include "net/base/net_errors.h" 13 #include "net/socket/socket.h" 14 15 namespace remoting { 16 17 namespace { 18 int kReadBufferSize = 4096; 19 } // namespace 20 21 SocketReader::SocketReader() 22 : socket_(NULL), 23 weak_factory_(this) { 24 } 25 26 SocketReader::~SocketReader() { 27 } 28 29 void SocketReader::Init(net::Socket* socket, 30 ReadResultCallback read_result_callback) { 31 DCHECK(socket); 32 DCHECK(!socket_); 33 34 socket_ = socket; 35 read_result_callback_ = read_result_callback; 36 DoRead(); 37 } 38 39 void SocketReader::DoRead() { 40 while (true) { 41 read_buffer_ = new net::IOBuffer(kReadBufferSize); 42 int result = socket_->Read( 43 read_buffer_.get(), 44 kReadBufferSize, 45 base::Bind(&SocketReader::OnRead, weak_factory_.GetWeakPtr())); 46 HandleReadResult(result); 47 if (result <= 0) 48 break; 49 } 50 } 51 52 void SocketReader::OnRead(int result) { 53 HandleReadResult(result); 54 if (result > 0) 55 DoRead(); 56 } 57 58 void SocketReader::HandleReadResult(int result) { 59 if (result != net::ERR_IO_PENDING) { 60 if (result < 0) 61 read_buffer_ = NULL; 62 base::ThreadTaskRunnerHandle::Get()->PostTask( 63 FROM_HERE, 64 base::Bind(&SocketReader::CallCallback, weak_factory_.GetWeakPtr(), 65 read_buffer_, result)); 66 } 67 } 68 69 void SocketReader::CallCallback(scoped_refptr<net::IOBuffer> data, int result) { 70 read_result_callback_.Run(data, result); 71 } 72 73 } // namespace remoting 74