// Copyright 2014 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.

#ifndef DEVICE_BLUETOOTH_BLUETOOTH_SOCKET_NET_H_
#define DEVICE_BLUETOOTH_BLUETOOTH_SOCKET_NET_H_

#include <queue>
#include <string>

#include "base/basictypes.h"
#include "base/memory/linked_ptr.h"
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/sequenced_task_runner.h"
#include "device/bluetooth/bluetooth_socket.h"
#include "device/bluetooth/bluetooth_socket_thread.h"
#include "net/base/net_log.h"
#include "net/socket/tcp_socket.h"

namespace net {
class IOBuffer;
class IOBufferWithSize;
}  // namespace net

namespace device {

// This class is a base-class for implementations of BluetoothSocket that can
// use net::TCPSocket. All public methods (including the factory method) must
// be called on the UI thread, while underlying socket operations are
// performed on a separate thread.
class BluetoothSocketNet : public BluetoothSocket {
 public:
  // BluetoothSocket:
  virtual void Close() OVERRIDE;
  virtual void Disconnect(const base::Closure& callback) OVERRIDE;
  virtual void Receive(int buffer_size,
                       const ReceiveCompletionCallback& success_callback,
                       const ReceiveErrorCompletionCallback& error_callback)
      OVERRIDE;
  virtual void Send(scoped_refptr<net::IOBuffer> buffer,
                    int buffer_size,
                    const SendCompletionCallback& success_callback,
                    const ErrorCompletionCallback& error_callback) OVERRIDE;

 protected:
  BluetoothSocketNet(scoped_refptr<base::SequencedTaskRunner> ui_task_runner,
                     scoped_refptr<BluetoothSocketThread> socket_thread,
                     net::NetLog* net_log,
                     const net::NetLog::Source& source);
  virtual ~BluetoothSocketNet();

  // Resets locally held data after a socket is closed. Default implementation
  // does nothing, subclasses may override.
  virtual void ResetData();

  // Methods for subclasses to obtain the members.
  scoped_refptr<base::SequencedTaskRunner> ui_task_runner() const {
    return ui_task_runner_;
  }

  scoped_refptr<BluetoothSocketThread> socket_thread() const {
    return socket_thread_;
  }

  net::NetLog* net_log() const { return net_log_; }
  const net::NetLog::Source& source() const { return source_; }

  net::TCPSocket* tcp_socket() { return tcp_socket_.get(); }

  void ResetTCPSocket();
  void SetTCPSocket(scoped_ptr<net::TCPSocket> tcp_socket);

  void PostSuccess(const base::Closure& callback);
  void PostErrorCompletion(const ErrorCompletionCallback& callback,
                           const std::string& error);

 private:
  struct WriteRequest {
    WriteRequest();
    ~WriteRequest();

    scoped_refptr<net::IOBuffer> buffer;
    int buffer_size;
    SendCompletionCallback success_callback;
    ErrorCompletionCallback error_callback;
  };

  void DoClose();
  void DoDisconnect(const base::Closure& callback);
  void DoReceive(int buffer_size,
                 const ReceiveCompletionCallback& success_callback,
                 const ReceiveErrorCompletionCallback& error_callback);
  void OnSocketReadComplete(
      const ReceiveCompletionCallback& success_callback,
      const ReceiveErrorCompletionCallback& error_callback,
      int read_result);
  void DoSend(scoped_refptr<net::IOBuffer> buffer,
              int buffer_size,
              const SendCompletionCallback& success_callback,
              const ErrorCompletionCallback& error_callback);
  void SendFrontWriteRequest();
  void OnSocketWriteComplete(const SendCompletionCallback& success_callback,
                             const ErrorCompletionCallback& error_callback,
                             int send_result);

  void PostReceiveCompletion(const ReceiveCompletionCallback& callback,
                             int io_buffer_size,
                             scoped_refptr<net::IOBuffer> io_buffer);
  void PostReceiveErrorCompletion(
      const ReceiveErrorCompletionCallback& callback,
      ErrorReason reason,
      const std::string& error_message);
  void PostSendCompletion(const SendCompletionCallback& callback,
                          int bytes_written);

  scoped_refptr<base::SequencedTaskRunner> ui_task_runner_;
  scoped_refptr<BluetoothSocketThread> socket_thread_;
  net::NetLog* net_log_;
  const net::NetLog::Source source_;

  scoped_ptr<net::TCPSocket> tcp_socket_;
  scoped_refptr<net::IOBufferWithSize> read_buffer_;
  std::queue<linked_ptr<WriteRequest> > write_queue_;

  DISALLOW_COPY_AND_ASSIGN(BluetoothSocketNet);
};

}  // namespace device

#endif  // DEVICE_BLUETOOTH_BLUETOOTH_SOCKET_NET_H_
