/*
 * OS specific functions for Fuchsia OS.
 *
 * Copyright (c) 2005-2009, Jouni Malinen <j@w1.fi>
 * Copyright (c) 2016 The Fuchsia Authors
 *
 * This software may be distributed under the terms of the BSD license.
 * See README for more details.
 *
 * OS specific functions for Fuchsia. Based off os_unix.c.
 */

#include "includes.h"

#include <sys/wait.h>
#include <time.h>

#include "common.h"
#include "os.h"

#ifdef WPA_TRACE

#include "list.h"
#include "trace.h"
#include "wpa_debug.h"

static struct dl_list alloc_list = DL_LIST_HEAD_INIT(alloc_list);

#define ALLOC_MAGIC 0xa84ef1b2
#define FREED_MAGIC 0x67fd487a

struct os_alloc_trace {
  unsigned int magic;
  struct dl_list list;
  size_t len;
  WPA_TRACE_INFO
} __attribute__((aligned(16)));

#endif /* WPA_TRACE */

void os_sleep(os_time_t sec, os_time_t usec) {
  if (sec) sleep(sec);
  if (usec) usleep(usec);
}

int os_get_time(struct os_time *t) {
  int res;
  struct timeval tv;
  res = gettimeofday(&tv, NULL);
  t->sec = tv.tv_sec;
  t->usec = tv.tv_usec;
  return res;
}

int os_get_reltime(struct os_reltime *t) {
#if defined(CLOCK_BOOTTIME)
  static clockid_t clock_id = CLOCK_BOOTTIME;
#elif defined(CLOCK_MONOTONIC)
  static clockid_t clock_id = CLOCK_MONOTONIC;
#else
  static clockid_t clock_id = CLOCK_REALTIME;
#endif
  struct timespec ts;
  int res;

  while (1) {
    res = clock_gettime(clock_id, &ts);
    if (res == 0) {
      t->sec = ts.tv_sec;
      t->usec = ts.tv_nsec / 1000;
      return 0;
    }
    switch (clock_id) {
#ifdef CLOCK_BOOTTIME
      case CLOCK_BOOTTIME:
        clock_id = CLOCK_MONOTONIC;
        break;
#endif
#ifdef CLOCK_MONOTONIC
      case CLOCK_MONOTONIC:
        clock_id = CLOCK_REALTIME;
        break;
#endif
      case CLOCK_REALTIME:
        return -1;
    }
  }
}

int os_mktime(int year, int month, int day, int hour, int min, int sec,
              os_time_t *t) {
  struct tm tm, *tm1;
  time_t t_local, t1, t2;
  os_time_t tz_offset;

  if (year < 1970 || month < 1 || month > 12 || day < 1 || day > 31 ||
      hour < 0 || hour > 23 || min < 0 || min > 59 || sec < 0 || sec > 60)
    return -1;

  memset(&tm, 0, sizeof(tm));
  tm.tm_year = year - 1900;
  tm.tm_mon = month - 1;
  tm.tm_mday = day;
  tm.tm_hour = hour;
  tm.tm_min = min;
  tm.tm_sec = sec;

  t_local = mktime(&tm);

  /* figure out offset to UTC */
  tm1 = localtime(&t_local);
  if (tm1) {
    t1 = mktime(tm1);
    tm1 = gmtime(&t_local);
    if (tm1) {
      t2 = mktime(tm1);
      tz_offset = t2 - t1;
    } else
      tz_offset = 0;
  } else
    tz_offset = 0;

  *t = (os_time_t)t_local - tz_offset;
  return 0;
}

int os_gmtime(os_time_t t, struct os_tm *tm) {
  struct tm *tm2;
  time_t t2 = t;

  tm2 = gmtime(&t2);
  if (tm2 == NULL) return -1;
  tm->sec = tm2->tm_sec;
  tm->min = tm2->tm_min;
  tm->hour = tm2->tm_hour;
  tm->day = tm2->tm_mday;
  tm->month = tm2->tm_mon + 1;
  tm->year = tm2->tm_year + 1900;
  return 0;
}

#define os_daemon daemon

int os_daemonize(const char *pid_file) {
  /* Not supported */
  return -1;
}

void os_daemonize_terminate(const char *pid_file) { /* Not supported */ }

int os_get_random(unsigned char *buf, size_t len) {
  FILE *f;
  size_t rc;

  if (TEST_FAIL()) return -1;

  /* TODO(alangardner): implement using random for now */
  f = fopen("/dev/urandom", "rb");
  if (f == NULL) {
    printf("Could not open /dev/urandom.\n");
    return -1;
  }

  rc = fread(buf, 1, len, f);
  fclose(f);

  return rc != len ? -1 : 0;
}

unsigned long os_random(void) { return random(); }

char *os_rel2abs_path(const char *rel_path) {
  char *buf = NULL, *cwd, *ret;
  size_t len = 128, cwd_len, rel_len, ret_len;
  int last_errno;

  if (!rel_path) return NULL;

  if (rel_path[0] == '/') return os_strdup(rel_path);

  for (;;) {
    buf = os_malloc(len);
    if (buf == NULL) return NULL;
    cwd = getcwd(buf, len);
    if (cwd == NULL) {
      last_errno = errno;
      os_free(buf);
      if (last_errno != ERANGE) return NULL;
      len *= 2;
      if (len > 2000) return NULL;
    } else {
      buf[len - 1] = '\0';
      break;
    }
  }

  cwd_len = os_strlen(cwd);
  rel_len = os_strlen(rel_path);
  ret_len = cwd_len + 1 + rel_len + 1;
  ret = os_malloc(ret_len);
  if (ret) {
    os_memcpy(ret, cwd, cwd_len);
    ret[cwd_len] = '/';
    os_memcpy(ret + cwd_len + 1, rel_path, rel_len);
    ret[ret_len - 1] = '\0';
  }
  os_free(buf);
  return ret;
}

int os_program_init(void) { return 0; }

void os_program_deinit(void) {
#ifdef WPA_TRACE
  struct os_alloc_trace *a;
  unsigned long total = 0;
  dl_list_for_each(a, &alloc_list, struct os_alloc_trace, list) {
    total += a->len;
    if (a->magic != ALLOC_MAGIC) {
      wpa_printf(MSG_INFO,
                 "MEMLEAK[%p]: invalid magic 0x%x "
                 "len %lu",
                 a, a->magic, (unsigned long)a->len);
      continue;
    }
    wpa_printf(MSG_INFO, "MEMLEAK[%p]: len %lu", a, (unsigned long)a->len);
    wpa_trace_dump("memleak", a);
  }
  if (total)
    wpa_printf(MSG_INFO, "MEMLEAK: total %lu bytes", (unsigned long)total);
#endif /* WPA_TRACE */
}

int os_setenv(const char *name, const char *value, int overwrite) {
  return setenv(name, value, overwrite);
}

int os_unsetenv(const char *name) { return unsetenv(name); }

char *os_readfile(const char *name, size_t *len) {
  FILE *f;
  char *buf;
  long pos;

  f = fopen(name, "rb");
  if (f == NULL) return NULL;

  if (fseek(f, 0, SEEK_END) < 0 || (pos = ftell(f)) < 0) {
    fclose(f);
    return NULL;
  }
  *len = pos;
  if (fseek(f, 0, SEEK_SET) < 0) {
    fclose(f);
    return NULL;
  }

  buf = os_malloc(*len);
  if (buf == NULL) {
    fclose(f);
    return NULL;
  }

  if (fread(buf, 1, *len, f) != *len) {
    fclose(f);
    os_free(buf);
    return NULL;
  }

  fclose(f);

  return buf;
}

int os_file_exists(const char *fname) {
  FILE *f = fopen(fname, "rb");
  if (f == NULL) return 0;
  fclose(f);
  return 1;
}

int os_fdatasync(FILE *stream) {
  if (!fflush(stream)) {
    return fdatasync(fileno(stream));
  }

  return -1;
}

#ifndef WPA_TRACE
void *os_zalloc(size_t size) { return calloc(1, size); }
#endif /* WPA_TRACE */

size_t os_strlcpy(char *dest, const char *src, size_t siz) {
  return strlcpy(dest, src, siz);
}

int os_memcmp_const(const void *a, const void *b, size_t len) {
  const u8 *aa = a;
  const u8 *bb = b;
  size_t i;
  u8 res;

  for (res = 0, i = 0; i < len; i++) res |= aa[i] ^ bb[i];

  return res;
}

#ifdef WPA_TRACE

#if defined(WPA_TRACE_BFD) && defined(CONFIG_TESTING_OPTIONS)
char wpa_trace_fail_func[256] = {0};
unsigned int wpa_trace_fail_after;

static int testing_fail_alloc(void) {
  const char *func[WPA_TRACE_LEN];
  size_t i, res, len;
  char *pos, *next;
  int match;

  if (!wpa_trace_fail_after) return 0;

  res = wpa_trace_calling_func(func, WPA_TRACE_LEN);
  i = 0;
  if (i < res && os_strcmp(func[i], __func__) == 0) i++;
  if (i < res && os_strcmp(func[i], "os_malloc") == 0) i++;
  if (i < res && os_strcmp(func[i], "os_zalloc") == 0) i++;
  if (i < res && os_strcmp(func[i], "os_calloc") == 0) i++;
  if (i < res && os_strcmp(func[i], "os_realloc") == 0) i++;
  if (i < res && os_strcmp(func[i], "os_realloc_array") == 0) i++;
  if (i < res && os_strcmp(func[i], "os_strdup") == 0) i++;

  pos = wpa_trace_fail_func;

  match = 0;
  while (i < res) {
    int allow_skip = 1;
    int maybe = 0;

    if (*pos == '=') {
      allow_skip = 0;
      pos++;
    } else if (*pos == '?') {
      maybe = 1;
      pos++;
    }
    next = os_strchr(pos, ';');
    if (next)
      len = next - pos;
    else
      len = os_strlen(pos);
    if (os_memcmp(pos, func[i], len) != 0) {
      if (maybe && next) {
        pos = next + 1;
        continue;
      }
      if (allow_skip) {
        i++;
        continue;
      }
      return 0;
    }
    if (!next) {
      match = 1;
      break;
    }
    pos = next + 1;
    i++;
  }
  if (!match) return 0;

  wpa_trace_fail_after--;
  if (wpa_trace_fail_after == 0) {
    wpa_printf(MSG_INFO, "TESTING: fail allocation at %s", wpa_trace_fail_func);
    for (i = 0; i < res; i++)
      wpa_printf(MSG_INFO, "backtrace[%d] = %s", (int)i, func[i]);
    return 1;
  }

  return 0;
}

char wpa_trace_test_fail_func[256] = {0};
unsigned int wpa_trace_test_fail_after;

int testing_test_fail(void) {
  const char *func[WPA_TRACE_LEN];
  size_t i, res, len;
  char *pos, *next;
  int match;

  if (!wpa_trace_test_fail_after) return 0;

  res = wpa_trace_calling_func(func, WPA_TRACE_LEN);
  i = 0;
  if (i < res && os_strcmp(func[i], __func__) == 0) i++;

  pos = wpa_trace_test_fail_func;

  match = 0;
  while (i < res) {
    int allow_skip = 1;
    int maybe = 0;

    if (*pos == '=') {
      allow_skip = 0;
      pos++;
    } else if (*pos == '?') {
      maybe = 1;
      pos++;
    }
    next = os_strchr(pos, ';');
    if (next)
      len = next - pos;
    else
      len = os_strlen(pos);
    if (os_memcmp(pos, func[i], len) != 0) {
      if (maybe && next) {
        pos = next + 1;
        continue;
      }
      if (allow_skip) {
        i++;
        continue;
      }
      return 0;
    }
    if (!next) {
      match = 1;
      break;
    }
    pos = next + 1;
    i++;
  }
  if (!match) return 0;

  wpa_trace_test_fail_after--;
  if (wpa_trace_test_fail_after == 0) {
    wpa_printf(MSG_INFO, "TESTING: fail at %s", wpa_trace_test_fail_func);
    for (i = 0; i < res; i++)
      wpa_printf(MSG_INFO, "backtrace[%d] = %s", (int)i, func[i]);
    return 1;
  }

  return 0;
}

#else

static inline int testing_fail_alloc(void) { return 0; }
#endif

void *os_malloc(size_t size) {
  struct os_alloc_trace *a;

  if (testing_fail_alloc()) return NULL;

  a = malloc(sizeof(*a) + size);
  if (a == NULL) return NULL;
  a->magic = ALLOC_MAGIC;
  dl_list_add(&alloc_list, &a->list);
  a->len = size;
  wpa_trace_record(a);
  return a + 1;
}

void *os_realloc(void *ptr, size_t size) {
  struct os_alloc_trace *a;
  size_t copy_len;
  void *n;

  if (ptr == NULL) return os_malloc(size);

  a = (struct os_alloc_trace *)ptr - 1;
  if (a->magic != ALLOC_MAGIC) {
    wpa_printf(MSG_INFO, "REALLOC[%p]: invalid magic 0x%x%s", a, a->magic,
               a->magic == FREED_MAGIC ? " (already freed)" : "");
    wpa_trace_show("Invalid os_realloc() call");
    abort();
  }
  n = os_malloc(size);
  if (n == NULL) return NULL;
  copy_len = a->len;
  if (copy_len > size) copy_len = size;
  os_memcpy(n, a + 1, copy_len);
  os_free(ptr);
  return n;
}

void os_free(void *ptr) {
  struct os_alloc_trace *a;

  if (ptr == NULL) return;
  a = (struct os_alloc_trace *)ptr - 1;
  if (a->magic != ALLOC_MAGIC) {
    wpa_printf(MSG_INFO, "FREE[%p]: invalid magic 0x%x%s", a, a->magic,
               a->magic == FREED_MAGIC ? " (already freed)" : "");
    wpa_trace_show("Invalid os_free() call");
    abort();
  }
  dl_list_del(&a->list);
  a->magic = FREED_MAGIC;

  wpa_trace_check_ref(ptr);
  free(a);
}

void *os_zalloc(size_t size) {
  void *ptr = os_malloc(size);
  if (ptr) os_memset(ptr, 0, size);
  return ptr;
}

char *os_strdup(const char *s) {
  size_t len;
  char *d;
  len = os_strlen(s);
  d = os_malloc(len + 1);
  if (d == NULL) return NULL;
  os_memcpy(d, s, len);
  d[len] = '\0';
  return d;
}

#endif /* WPA_TRACE */

int os_exec(const char *program, const char *arg, int wait_completion) {
  /* TODO(alangardner): Implement using launchpad */
  pid_t pid;
  int pid_status;

  pid = fork();
  if (pid < 0) {
    perror("fork");
    return -1;
  }

  if (pid == 0) {
    /* run the external command in the child process */
    const int MAX_ARG = 30;
    char *_program, *_arg, *pos;
    char *argv[MAX_ARG + 1];
    int i;

    _program = os_strdup(program);
    _arg = os_strdup(arg);

    argv[0] = _program;

    i = 1;
    pos = _arg;
    while (i < MAX_ARG && pos && *pos) {
      while (*pos == ' ') pos++;
      if (*pos == '\0') break;
      argv[i++] = pos;
      pos = os_strchr(pos, ' ');
      if (pos) *pos++ = '\0';
    }
    argv[i] = NULL;

    execv(program, argv);
    perror("execv");
    os_free(_program);
    os_free(_arg);
    exit(0);
    return -1;
  }

  if (wait_completion) {
    /* wait for the child process to complete in the parent */
    waitpid(pid, &pid_status, 0);
  }

  return 0;
}
