//===-- IOStream.cpp --------------------------------------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "IOStream.h"

#if defined(_WIN32) 
#include <io.h>
#else
#include <netinet/in.h>
#include <sys/socket.h>
#include <unistd.h>
#endif

#include <fstream>
#include <string>
#include <vector>

using namespace lldb_vscode;

StreamDescriptor::StreamDescriptor() {}

StreamDescriptor::StreamDescriptor(StreamDescriptor &&other) {
  *this = std::move(other);
}

StreamDescriptor::~StreamDescriptor() {
  if (!m_close)
    return;

  if (m_is_socket)
#if defined(_WIN32)
    ::closesocket(m_socket);
#else
    ::close(m_socket);
#endif
  else
    ::close(m_fd);
}

StreamDescriptor &StreamDescriptor::operator=(StreamDescriptor &&other) {
  m_close = other.m_close;
  other.m_close = false;
  m_is_socket = other.m_is_socket;
  if (m_is_socket)
    m_socket = other.m_socket;
  else
    m_fd = other.m_fd;
  return *this;
}

StreamDescriptor StreamDescriptor::from_socket(SOCKET s, bool close) {
  StreamDescriptor sd;
  sd.m_is_socket = true;
  sd.m_socket = s;
  sd.m_close = close;
  return sd;
}

StreamDescriptor StreamDescriptor::from_file(int fd, bool close) {
  StreamDescriptor sd;
  sd.m_is_socket = false;
  sd.m_fd = fd;
  sd.m_close = close;
  return sd;
}

bool OutputStream::write_full(llvm::StringRef str) {
  while (!str.empty()) {
    int bytes_written = 0;
    if (descriptor.m_is_socket)
      bytes_written = ::send(descriptor.m_socket, str.data(), str.size(), 0);
    else
      bytes_written = ::write(descriptor.m_fd, str.data(), str.size());

    if (bytes_written < 0) {
      if (errno == EINTR || errno == EAGAIN)
        continue;
      return false;
    }
    str = str.drop_front(bytes_written);
  }

  return true;
}

bool InputStream::read_full(std::ofstream *log, size_t length,
                            std::string &text) {
  std::string data;
  data.resize(length);

  char *ptr = &data[0];
  while (length != 0) {
    int bytes_read = 0;
    if (descriptor.m_is_socket)
      bytes_read = ::recv(descriptor.m_socket, ptr, length, 0);
    else
      bytes_read = ::read(descriptor.m_fd, ptr, length);

    if (bytes_read == 0) {
      if (log)
        *log << "End of file (EOF) reading from input file.\n";
      return false;
    }
    if (bytes_read < 0) {
      int reason = 0;
#if defined(_WIN32)
      if (descriptor.m_is_socket)
        reason = WSAGetLastError();
      else
        reason = errno;
#else
      reason = errno;
      if (reason == EINTR || reason == EAGAIN)
        continue;
#endif

      if (log)
        *log << "Error " << reason << " reading from input file.\n";
      return false;
    }

    assert(bytes_read >= 0 && (size_t)bytes_read <= length);
    ptr += bytes_read;
    length -= bytes_read;
  }
  text += data;
  return true;
}

bool InputStream::read_line(std::ofstream *log, std::string &line) {
  line.clear();
  while (true) {
    if (!read_full(log, 1, line))
      return false;

    if (llvm::StringRef(line).endswith("\r\n"))
      break;
  }
  line.erase(line.size() - 2);
  return true;
}

bool InputStream::read_expected(std::ofstream *log, llvm::StringRef expected) {
  std::string result;
  if (!read_full(log, expected.size(), result))
    return false;
  if (expected != result) {
    if (log)
      *log << "Warning: Expected '" << expected.str() << "', got '" << result
           << "\n";
  }
  return true;
}
