// Copyright 2018 The Fuchsia 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 <dirent.h>
#include <errno.h>
#include <fcntl.h>
#include <fuchsia/hardware/serial/llcpp/fidl.h>
#include <lib/fdio/unsafe.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <threads.h>
#include <unistd.h>
#include <zircon/syscalls.h>

#define DEV_SERIAL "/dev/class/serial"

namespace fuchsia = ::llcpp::fuchsia;

static void serial_print(int fd, const char* str) { write(fd, str, strlen(str)); }

int main(int argc, char** argv) {
  struct dirent* de;
  DIR* dir = opendir(DEV_SERIAL);
  if (!dir) {
    printf("Error opening %s\n", DEV_SERIAL);
    return -1;
  }

  int fd = -1;
  char path[100];

  while ((de = readdir(dir)) != NULL) {
    if (!strcmp(de->d_name, ".") || !strcmp(de->d_name, "..")) {
      continue;
    }

    snprintf(path, sizeof(path), "%s/%s", DEV_SERIAL, de->d_name);
    fd = open(path, O_RDWR);
    if (fd < 0) {
      continue;
    }

    fdio_t* fdio = fdio_unsafe_fd_to_io(fd);
    auto result = fuchsia::hardware::serial::Device::Call::GetClass(
        zx::unowned_channel(fdio_unsafe_borrow_channel(fdio)));
    fuchsia::hardware::serial::Class device_class = result->device_class;
    fdio_unsafe_release(fdio);
    if (!result.ok() || device_class != fuchsia::hardware::serial::Class::GENERIC) {
      close(fd);
      continue;
    } else {
      break;
    }
  }

  if (fd < 0) {
    fprintf(stderr, "could not find generic serial port in %s\n", DEV_SERIAL);
    return -1;
  }

  while (1) {
    char buffer[100];
    ssize_t count = read(fd, buffer, sizeof(buffer));
    if (count < 0) {
      fprintf(stderr, "serial read failed: %s\n", strerror(errno));
      break;
    }

    // echo text locally
    for (ssize_t i = 0; i < count; i++) {
      printf("%c", buffer[i]);
    }
    fflush(stdout);

    if (buffer[0] == 'x' || buffer[0] == 'X') {
      serial_print(fd, "Closing and reopening the serial port. Wish me luck!\n");
      // wait for data to be written before closing handle
      // TODO(voydanoff) eliminate this sleep after we implement socket_flush()
      sleep(1);
      close(fd);
      // wait a bit for serial port to shut down before reopening
      sleep(1);
      fd = open(path, O_RDWR);
      if (fd < 0) {
        fprintf(stderr, "failed to reopen serial port: %s\n", strerror(errno));
        return fd;
      }
      serial_print(fd, "...and we're back!\n");
    } else {
      serial_print(fd, "Read: \"");
      write(fd, buffer, count);
      serial_print(fd, "\"\n");
    }
  }

  close(fd);

  return 0;
}
