// Copyright 2011 Google Inc. All Rights Reserved.
// Author: qianzhang@google.com (Qian Zhang)

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <inttypes.h>
#include <assert.h>
#include "utility.h"
#include "hdhomerun_plugin.h"
#include "libhdhomerun/hdhomerun.h"
#include "hdhomerun_tuner.h"
#include "hdhomerun_dev.h"
#include "hdhomerun_tuner.h"
#include "channel_buffer.h"
#include "sagelog.h"

#define MAX_TUNER_NUM 16

struct device_list {
  int tuner_num;
  int list_num;
  struct hdhr_tuner_t *hdhrs;
};

static int discover_hdhrs(struct hdhr_tuner_t *ht, int max_ht_num)
{
  int i, ret = 0;
  ret = discover_device(ht, max_ht_num);
  if (ret > 0) {
    for (i = 0; i < ret; i++) {
      // if a unit shares a source input in a device, copy data.
      if (i > 0 && tuner_input_sharing(&ht[i - 1], &ht[i])) {
        ht[i].cc_tuner = ht[i - 1].cc_tuner;
        strncpy(ht[i].model, ht[i - 1].model, sizeof(ht[i].model));
      } else
        get_dev_model(&ht[i]);
    }
    return i;
  }
  return 0;
}

void *dev_init(int *num)
{
  int i, index = 0, tuner_num;
  struct device_list *devices;

  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun device init"));

  devices = (struct device_list *)malloc(sizeof(struct device_list));
  if (devices != NULL) {
    devices->hdhrs = (struct hdhr_tuner_t *)malloc(sizeof(struct hdhr_tuner_t) *
                                                   MAX_TUNER_NUM);
    memset(devices->hdhrs, 0,
           sizeof(sizeof(struct hdhr_tuner_t) * MAX_TUNER_NUM));
    if (devices->hdhrs == NULL) {
      free(devices);
      return 0;
    }
    devices->list_num = MAX_TUNER_NUM;
    devices->tuner_num = 0;
    tuner_num = discover_hdhrs(devices->hdhrs, MAX_TUNER_NUM);
    for (i = 0; i < tuner_num; i++) {
      devices->hdhrs[i].tuner_id = index++;
      snprintf(devices->hdhrs[i].tuner_name,
               sizeof(devices->hdhrs[i].tuner_name), "%s-%s",
               devices->hdhrs[i].model, devices->hdhrs[i].name);
      devices->tuner_num++;
      sage_log((_LOG_TRACE, 3, "hdhr:%d %s %s %s", i,
                devices->hdhrs[i].tuner_name, devices->hdhrs[i].model,
                devices->hdhrs[i].cc_tuner ? "CableCard" : ""));
    }
    devices->tuner_num = tuner_num;
    *num = tuner_num;
    return devices;
  }
  return NULL;
}

void dev_release(void *handle)
{
  struct device_list *devices = (struct device_list *)handle;
  if (devices != NULL) {
    if (devices->hdhrs != NULL)
      free(devices->hdhrs);
    free(devices);
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun device release."));
}

int get_dev_name(void *handle, int index, char *name, int max_name_len)
{
  struct device_list *devices = (struct device_list *)handle;
  if (devices != NULL && index < devices->tuner_num) {
    struct hdhr_tuner_t *hdhr = &devices->hdhrs[index];
    strncpy(name, hdhr->tuner_name, max_name_len);
    return 1;
  }
  return 0;
}

void *dev_open(void *handle, int index, int attr)
{
  struct device_list *devices = (struct device_list *)handle;
  struct hdhr_tuner_t *hdhr;
  if (index >= devices->tuner_num)
    return NULL;
  hdhr = &devices->hdhrs[index];
  hdhr->hd = open_hdhr(hdhr->name);
  return hdhr;
}

void dev_close(void *dev)
{
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return;
  }
  stop_channel(hdhr->hd);
  close_hdhr(hdhr->hd);
}

int dev_tune(void *dev, char *channel, char *stream_tar)
{
  int ret;
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return 0;
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun tune %s %s.", hdhr->name,
            (char *)channel));
  if (strstr(stream_tar, "udp://") == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: stream target \"%s\" is wrong.",
              stream_tar));
    return 0;
  }

  if (hdhr->cc_tuner) {
    // HDHomeRun PRIME
    if (strstr(channel, "vchan:") == NULL) {
      char vchan[32];
      snprintf(vchan, sizeof(vchan), "vchan:%d", atoi(channel));
      ret = tune_channel(hdhr->hd, vchan, "", stream_tar);
    } else
      ret = tune_channel(hdhr->hd, channel, "", stream_tar);
  } else {
    // HDHomeRun US
    char tune_str[32], map_str[32], prog_str[8];
    int ch = -1, prog = -1, vch_major = -1, vch_minor = -1;
    char *ps, *pe;
    map_str[0] = 0x0;

    // channel format: xx-yy-zz
    // xx=physical channel, yy=virtual major channel, zz=virtual minor channel
    if (sscanf(channel, "%d-%d-%d", &ch, &vch_major, &vch_minor) == 3) {
      ret = tune_atsc_vchannel(hdhr->hd, ch, vch_major, vch_minor, stream_tar);
      goto out;
    }

    // channel format: xx-yy
    // xx=physical channel, yy=virtual major channel
    if (sscanf(channel, "%d-%d", &ch, &vch_major) == 2) {
      vch_minor = 0;
      ret = tune_atsc_vchannel(hdhr->hd, ch, vch_major, vch_minor, stream_tar);
      goto out;
    }

    // if channel in format "map:xxx-yy|auto:zzz prog:ppp"
    if ((ps = strstr(channel, "map:")) != NULL &&
        (pe = strchr(ps + 4, '|')) != NULL) {
      strncpy(map_str, ps + 4, pe - (ps + 4));
      map_str[pe - (ps + 4)] = 0x0;
    }
    get_int_val_by_name(channel, "auto", &ch, NULL);
    get_int_val_by_name(channel, "prog", &prog, NULL);
    if (prog == -1) {
      sage_log(
          (_LOG_TRACE, 3, "hdhr:ERROR: invalid channel string %s", channel));
      return 0;
    }
    // if channel in format "nnn prog:mmm", based on dev to guess map
    if (map_str[0] == 0x0 && prog > 0 && ch == -1) {
      ch = atoi(channel);
      if (ch > 0) {
        snprintf(map_str, sizeof(map_str), "map:us-bcast");
      }
    }
    if (map_str[0] && ch > 0 && prog > 0) {
      snprintf(tune_str, sizeof(tune_str), "%s|auto:%d", map_str, ch);
      snprintf(prog_str, sizeof(prog), "%d", prog);
      ret = tune_channel(hdhr->hd, tune_str, prog_str, stream_tar);
    } else {
      sage_log(
          (_LOG_ERROR, 3, "hdhr:ERROR: invalid channel string %s", channel));
      return 0;
    }
  }

out:
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun tune %s %s.", (char *)channel,
            ret > 0 ? "successful" : "failed"));
  return ret > 0;
}

int dev_stop(void *dev)
{
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return 0;
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun stop %s.", (char *)hdhr->name));
  int ret = stop_channel(hdhr->hd);
  return ret > 0;
}

int dev_scan(void *dev, char *tuner_name, char *channel,
             struct channel_list_t **cl_p)
{
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return 0;
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun scan %s.", (char *)hdhr->name));
  if (hdhr->cc_tuner) {
    int vchannel;
    char *p;
    if ((p = strstr(channel, "vchan:")) == NULL)
      vchannel = atoi(channel);
    else
      vchannel = atoi(p + 6);
    if (vchannel == 0)
      return 0;

    struct channel_list_t *cl = _create_channel_list(1);
    int ret = scan_vchannel(hdhr->hd, vchannel, cl->ce);
    char unit_name[16];
    snprintf(cl->ce[0].dev_name, sizeof(cl->ce[0].dev_name) - 1, "HDHR.%s",
             get_unit_name(hdhr, unit_name, sizeof(unit_name)));
    cl->channel_num = ret;
    if (ret == 0) {
      _release_channel_list(cl);
      cl = NULL;
    }
    if (cl_p != NULL)
      *cl_p = cl;
    return ret;
  } else {
    sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun ATSC dev_scan not implemented %s.",
              (char *)hdhr->name));
  }

  return 0;
}

static struct channel_list_t *build_hdhr_channel_table(
    struct hdhr_tuner_t *hdhr)
{
  if (hdhr->cc_tuner) {
    struct vchan_tbl_t *vt = create_vchan_tbl(hdhr);
    struct channel_list_t *cl = NULL;
    if (get_vchannel_list(vt) > 0) {
      int num = vt->channel_num;
      cl = _create_channel_list(num);
      int i;
      for (i = 0; i < num; i++) {
        char unit_name[16];
        cl->ce[i].state = 1;
        snprintf(cl->ce[i].dev_tuning, sizeof(cl->ce[i].dev_tuning) - 1,
                 "vchan:%d", vt->vchan[i].guide_id);
        snprintf(cl->ce[i].ch_name, sizeof(cl->ce[i].ch_name) - 1, "%d",
                 vt->vchan[i].guide_id);
        strncpy(cl->ce[i].ch_desc, vt->vchan[i].guide_name,
                sizeof(cl->ce[i].ch_desc) - 1);
        cl->ce[i].src_ip[0] = 0x0;
        cl->ce[i].src_port = 0;  // dynamic assigning
        snprintf(cl->ce[i].dev_name, sizeof(cl->ce[i].dev_name) - 1, "HDHR.%s",
                 get_unit_name(hdhr, unit_name, sizeof(unit_name)));
        cl->ce[i].ch = vt->vchan[i].guide_id;
        cl->ce[i].frq = 0;
        cl->ce[i].av_inf[0] = 0;
      }
      cl->channel_num = i;
    }
    release_vchan_tbl(vt);
    return cl;
  } else {
    sage_log(
        (_LOG_TRACE, 3,
         "hdhr:hdhomerun ATSC build_hdhr_channel_table not implemented %s.",
         (char *)hdhr->name));
  }
  return NULL;
}

int dev_build_channel_table(void *dev, char *option,
                            struct channel_list_t **cl_p)
{
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return 0;
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun dev_build_channel_table %s.",
            (char *)hdhr->name));
  struct channel_list_t *cl = build_hdhr_channel_table(hdhr);
  if (cl_p != NULL) {
    *cl_p = cl;
    if (cl == NULL)
      return 0;
    return cl->channel_num;
  }
  return 0;
}

int dev_release_channel_table(void *dev)
{
  struct hdhr_tuner_t *hdhr = (struct hdhr_tuner_t *)dev;
  if (hdhr == NULL) {
    sage_log((_LOG_TRACE, 3, "hdhr:ERROR: invalid device handle."));
    return 0;
  }
  sage_log((_LOG_TRACE, 3, "hdhr:hdhomerun dev_release_channel_table %s.",
            (char *)hdhr->name));
  if (hdhr->channel_table != NULL) {
    free(hdhr->channel_table);
    hdhr->channel_table = NULL;
    return 1;
  } else {  // TODO
  }
  return 0;
}
